255 20 打赏 收藏 转发到动态 举报
写回复
用AI写文章
20 条回复
切换为时间正序
请发表友善的回复…
发表回复
dracowk 2010-04-09
  • 打赏
  • 举报
回复
呃,还是running的比赛,就来这里求助了……
zyl072 2010-04-09
  • 打赏
  • 举报
回复
第四题:
简单题,模拟一下栈的操作就行了。
若栈顶元素等于当前元素,则弹出。
否则若下一个入栈元素小于当前元素,则说明出错,跳出循环。
否则继续压栈直到压入元素等于当前元素为止。

00376229 2010-04-09 19:30:35 Accepted 1004 31 MS 284 KB GNU C++

#include <stdio.h>
#include <string.h>

#define MAXN 10010
int a[MAXN], stack[MAXN];
int n, top;



int main(){
int i, next, k;
for (scanf("%d", &n); n; scanf("%d", &n)){
for (i=1; i<=n; ++i)
scanf("%d", a+i);
top = 0;
next = 1;
for (i=1; i<=n; ++i){
if (top && stack[top] == a[i])
top--;
else if (a[i] < next)
break;
else {
while (next < a[i])
stack[++top] = next++;
++next;
}
}
puts(i<=n ? "No":"Yes");
}
}




第五题:
把任务按开始时间排序。
然后设一个变量作为当前时间依次处理任务:
循环(对于每一个任务)
若当前时间小于任务进入队列时间,则当前时间等于任务进入队列时间。
当前时间 += 任务运行时间
总时间 += 当前时间 - 任务进入队列时间

输出:总时间/任务数

00376251 2010-04-09 19:44:29 Accepted 1005 0 MS 228 KB GNU C++

#include <stdio.h>
#include <algorithm>
using namespace std;

int n;
struct _task{
double start_time;
double run_time;
bool operator < (const _task &other) const{
return start_time < other.start_time;
}
} task[110];

int main(){
int i;
double tot_time = 0,current_time = 0;
scanf("%d", &n);
for (i=0; i<n; ++i)
scanf("%lf %lf", &task[i].start_time, &task[i].run_time);
sort(task, task+n); // 按开始时间排序
for (i=0; i<n; ++i){
if (current_time < task[i].start_time)
current_time = task[i].start_time;
current_time += task[i].run_time;
tot_time += current_time - task[i].start_time;
}
printf("%.4lf\n", tot_time/n);
}



第六题:
就模拟手算,逐列的消元,就可以了。
对于每一列,选一个该列不为0的行。
然后用这一行将其他该列不为0的行的这一列消为0(说的很绕口)。

代码:
00376430 2010-04-09 21:14:16 Accepted 1006 0 MS 208 KB GNU C++


#include <stdio.h>

int n, m;

struct _line {
int data[12];

void operator -= (const _line &other) {
int i;
for (i=0; i<m; ++i)
data[i] -= other.data[i];
}
void operator *= (const int value) {
int i;
for (i=0; i<m; ++i)
data[i] *= value;
}
} line[12];

int gcd(int a,int b){
return b ? gcd(b, a%b) : a;
}

int main(){
int i, j, k, s, ans;
for (scanf("%d %d", &n, &m); n; scanf("%d %d", &n, &m)){

for (i=0; i<n; ++i)
for (j=0; j<m; ++j)
scanf("%d", line[i].data + j);
ans = 0;

for (i=0; i<m; ++i){
for (j=0; j<n; ++j)
if (line[j].data[i])
break;
if (j>=n)
continue;

ans++;
if (line[j].data[i] < 0)
line[j] *= -1;

for (k=0; k<n; ++k)
if (k!=j && line[k].data[i]) {
_line temp = line[j];
if (line[k].data[i] < 0)
line[k] *= -1;
s = gcd(line[k].data[i], temp.data[i]);
temp *= line[k].data[i] / s;
line[k] *= line[j].data[i] / s;
line[k] -= temp;
}
line[j] = line[--n]; // 消除第j行
}
printf("%d\n", ans);
}
}


六CD 2010-04-09
  • 打赏
  • 举报
回复
帮顶。。。。。。。。。。。。。。。。。。。。。。
zyl072 2010-04-09
  • 打赏
  • 举报
回复
第三题,纯水题,用strstr就能搞定:

00376212 2010-04-09 19:18:27 Accepted 1003 0 MS 212 KB GNU C++


#include <stdio.h>
#include <string.h>

char str[300], key[20];

int main(){
char ch, *p;
while (scanf("%s", str)!=EOF) {
for (scanf("%s", key); strcmp(key, "END"); scanf("%s", key)){
if (strcmp(key, "NULL") == 0){
puts("0 NULL");
continue;
}
if ( (p = strstr(str, key)) ){
ch = *p;
*p = '\0';
printf("%d %s\n", strlen(str), str[0]?str:"NULL");
*p = ch;
} else {
printf("%d %s\n", strlen(str), str);
}
}

}
}
zyl072 2010-04-09
  • 打赏
  • 举报
回复
第二题:
将关系反过来记录,即将 A作业 需要 B作业先完成,记录成 B作业 是 A作业的前提作业。

再建一个队列。初始状态下将所有入度为0(即没有前置作业)的作业加入队列。
然后从队列中开始处理。

每处理一个作业,将他所能影响的作业的入度 - 1,若减1之后入度为0,则将该节点也加入队列。
始终记录一个最大值,输出即可:

C++代码:
00376165 2010-04-09 18:56:46 Accepted 1002 125 MS 2120 KB GNU C++


#include <stdio.h>
#include <string.h>
#include <vector>
using namespace std;

#define MAXN 10010
#define MAXM 104

int a[MAXN], ans[MAXN], list[MAXN] , degree[MAXN];
vector <int> next[MAXN]; // 记录关系,next[i][j] 表示 j作业需要先完成i作业
int n, m;

int main(){
int cases;
int i, j, k, max;
scanf("%d", &cases);
while (cases--) {
scanf("%d", &n);
memset(ans, -1, sizeof ans);
m = 0;
for (i=1; i<=n; ++i)
next[i].clear();
for (i=1; i<=n; ++i){
scanf("%d %d", a+i, degree+i);

if (degree[i] == 0){ // 入度为0的节点加入初始队列。
list[m++] = i;
ans[i] = 0;
}
for (j=0; j<degree[i]; ++j){
scanf("%d", &k);
next[k].push_back(i); // 节点K影响节点I
}
}
max = 0;
for (i=0; i<m; ++i){ // 开始处理队列
k = list[i];
ans[k] += a[k];
if (ans[k] > max) // 更新最大值
max = ans[k];
for (j=next[k].size()-1; j>=0; --j){ // 枚举该节点所能影响到的所有节点
if (ans[k] > ans[next[k][j]]) // 更新该作业可开始的最早时间
ans[next[k][j]] = ans[k];
if (--degree[next[k][j]] == 0){ // 若该节点入度为0,则加入队列。
list[m++] = next[k][j];
}
}
}
if (m != n) // 若队列中不足N个作业,说明作业没处理完
puts("No Solution.");
else
printf("%d\n", max);
}
}

zyl072 2010-04-09
  • 打赏
  • 举报
回复
第一题:哈夫曼树,用一个最小堆,每次选两个最小的长度求和,将和加到最终结果中,并再插入到堆中。
这个过程执行N-1次以后,堆中只剩一个元素,最终结果即为所求:

代码:


#include <stdio.h>
#include <queue>
#include <vector>
using namespace std;

priority_queue <int,vector <int>, greater<int> > heap;

int main(){
int i, k, n, ans = 0;
scanf("%d", &n);
for (i=0; i<n; ++i){
scanf("%d", &k);
heap.push(k);
}
for (i=1; i<n; ++i){
k = heap.top();
heap.pop();
k += heap.top();
heap.pop();
ans += k;
heap.push(k);
}
printf("%d\n", ans);
}


提交结果:
00376117 2010-04-09 18:06:54 Accepted 1001 93 MS 1312 KB GNU C++
Arucart 2010-04-09
  • 打赏
  • 举报
回复
e...第一题就被难住了...恩,下午不无聊了也
dweqd 2010-04-09
  • 打赏
  • 举报
回复
[Quote=引用 13 楼 dracowk 的回复:]
呃,还是running的比赛,就来这里求助了……
[/Quote]
呵呵,比赛早结束了!牛人都知道这是水题!都会懒得写代码,我只是想看看有没有更好的解法!
hua_zhixing_ 2010-04-08
  • 打赏
  • 举报
回复
做OJ的挺多的嘛……
knate 2010-04-08
  • 打赏
  • 举报
回复
好奇问一句,
这些解释不能用C++标准库?
dweqd 2010-04-08
  • 打赏
  • 举报
回复
[Quote=引用 7 楼 qq120848369 的回复:]
其他的不会。我再考虑一下第二题
[/Quote]
其他的题目代码,谢了啊!
dweqd 2010-04-08
  • 打赏
  • 举报
回复
[Quote=引用 7 楼 qq120848369 的回复:]
其他的不会。我再考虑一下第二题
[/Quote]
额,加个代码吧
renzhewh 2010-04-08
  • 打赏
  • 举报
回复
1003 visual C

#include <stdio.h>
#include <string.h>

int SafeStrcpy(char *dst, const char *src, int size, char *key)
{
int len = strlen(src);

char *location = strstr(src, key);
if (location != NULL)
len = location - src;

strncpy(dst, src, len); /* 这句可不要 */

return len;
}

void test(void)
{
enum {BUFFER_SIZE = 256, KEY_SIZE = 16};

char input[BUFFER_SIZE] = "";
char output[BUFFER_SIZE] = "";
char key[KEY_SIZE] = "";

int len = 0; /* 用于记录所拷贝字符串的长度 */

while (scanf("%s%*c", input) != EOF)
{
while (1)
{
scanf("%s%*c", key);

if (strcmp(key, "END") == 0)
break;
if (strcmp(key, "NULL") == 0)
key[0] = 0;

len = SafeStrcpy(output, input, BUFFER_SIZE, key);
if (len == 0)
printf("0 NULL\n");
else
printf("%d %.*s\n", len, len, output);
}
}
}

int main()
{
test();

return 0;
}
qq120848369 2010-04-08
  • 打赏
  • 举报
回复
其他的不会。我再考虑一下第二题
qq120848369 2010-04-08
  • 打赏
  • 举报
回复
第五题: 就是个调度问题。

开始时间t1 结束时间t2
0 0 ->存入time[0]
1 2.5 ->存入time[1]
3 6 ->存入time[2]
5 11 ->存入time[3]
7 13 ->存入time[4]

设置初始t1=t2=0
第一个任务开始1,1>time[0],time[1]=1+1.5=2.5
第二个任务开始3, 3>time[1],time[2]=3+3=6
第三个任务开始5, 5<time[2],time[3]=time[2]+5=11
第四个任务开始7.5,7.5<time[3], time[4]=time[3]+2=13
fansOfBnb 2010-04-08
  • 打赏
  • 举报
回复
顶.......
qq120848369 2010-04-08
  • 打赏
  • 举报
回复
第四题:模拟栈的运行过程就可以了.

举例:3,4,2,1,5, i作指示,从3开始

我们开始模拟: 1进 ,栈顶非3 ,2进,栈顶非3, 3进, 栈顶3与i指示相同, i++, 3退栈, 4进,栈顶与i指示相同,4退栈,i++,栈顶与i指示相同,2退栈,i++ ,栈顶与指示i相同,1退栈,i++ ,5进, 栈顶与i指示相同,5退。 i走到头,结束,yes。 如果进栈的数累计超过5个,那么就no了,。
qq120848369 2010-04-08
  • 打赏
  • 举报
回复
第二题,我猜是图的拓扑序列上做文章
qq120848369 2010-04-08
  • 打赏
  • 举报
回复
第一题:贪心,哈夫曼树一样的.
xiaolinxianju 2010-04-08
  • 打赏
  • 举报
回复
顶~楼主~

33,009

社区成员

发帖
与我相关
我的任务
社区描述
数据结构与算法相关内容讨论专区
社区管理员
  • 数据结构与算法社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧