Time Limit : 3000/1000ms (Java/Other) Memory Limit : 65535/32768K (Java/Other)
Total Submission(s) : 4 Accepted Submission(s) : 1
Font: Times New Roman | Verdana | Georgia
Font Size: ← →
Problem Description
lt最近阅读了CPU构造相关的文章,了解到了CPU为了提高执行效率,会将尽可能多的指令同时执行。为了让自己的代码能够运行得更快,lt开始尝试写出能够利用这种同时执行机制的代码。
现在,请你写一个程序判断lt的代码在同时执行机制下所需要消耗的最短时间。
为了简化情况,我们假设lt的CPU有a-e五个存储数据的单元,并且CPU资源足够(能同时执行任意条指令),各种指令执行的时间一样,都为1个单位。
lt的代码由以下几种格式的指令组成:
mov x1,x2 ---- 读取x1存储单元的数据,然后写入到x2。x1和x2不会是同一个存储单元。
add x1,x2 ---- 读取x1和x2存储单元的数据,然后把x1+x2的结果写入到x2。
x1,x2代表a-e五个存储单元中的某一个,字符'#'代表一段代码结束。
从lt所看的文章中我们得知:
1.当两条指令的数据存在依赖时,这两条指令不能并行执行。比如:
mov a,b
mov b,c
由于第二条指令需要读取b单元的数据,而b单元的数据要从a单元获得,因此第二条指令只能等第一条执行完。
2.同时执行的结果要与顺序执行的结果一致,比如:
mov a,c
mov b,c
为了保证这两条指令执行完后c单元中的结果是从b单元来的,这两条指令也只能顺序执行。
现在,请你写一个程序判断lt的代码在同时执行机制下所需要消耗的最短时间。
为了简化情况,我们假设lt的CPU有a-e五个存储数据的单元,并且CPU资源足够(能同时执行任意条指令),各种指令执行的时间一样,都为1个单位。
lt的代码由以下几种格式的指令组成:
mov x1,x2 ---- 读取x1存储单元的数据,然后写入到x2。x1和x2不会是同一个存储单元。
add x1,x2 ---- 读取x1和x2存储单元的数据,然后把x1+x2的结果写入到x2。
x1,x2代表a-e五个存储单元中的某一个,字符'#'代表一段代码结束。
从lt所看的文章中我们得知:
1.当两条指令的数据存在依赖时,这两条指令不能并行执行。比如:
mov a,b
mov b,c
由于第二条指令需要读取b单元的数据,而b单元的数据要从a单元获得,因此第二条指令只能等第一条执行完。
2.同时执行的结果要与顺序执行的结果一致,比如:
mov a,c
mov b,c
为了保证这两条指令执行完后c单元中的结果是从b单元来的,这两条指令也只能顺序执行。
Input
第一个数字代表代码的段数n,接下来是按照题目格式所写出的n段代码,一段代码以'#'结尾,有多段代码。
Output
每段代码所运行的最短时间,每个一行。
Sample Input
2 mov a,b mov b,c mov a,d # mov a,b mov b,c add b,c #
Sample Output
2 3 Hint: 第一段代码中的第一,三条指令可以并行执行,而第二条与第一条指令存在数据依赖,只能等待第一条执行完毕。因此消耗的时间为2个单位。 第二段代码中第一,二条指令存在数据依赖,无法并行;而为了保证结果正确,第三条与第二条也不能并行。因此消耗的时间为3个单位。
解题说明:此题是一道模拟题
#include<iostream>
using namespace std;
struct CMD
{
int type;
int op1, op2;
int time;
};
int max(int a, int b)
{
return a > b ? a : b;
}
int findrela(CMD arr[], CMD &cmd, int pos)
{
int maxpos = -1, time = 0;
while (pos >= 0)
{
if (arr[pos].op2 == cmd.op1 || arr[pos].op2 == cmd.op2 || arr[pos].op1 == cmd.op2)
{
if (time <= arr[pos].time)
{
maxpos = pos;
time = arr[maxpos].time;
}
}
pos--;
}
return maxpos;
}
int main()
{
int T;
cin >> T;
getchar();
while (T--)
{
char tmp[100];
CMD cmds[20];
int pos = 0;
while (true)
{
gets(tmp);
if (tmp[0] == 'm')
{
CMD t = { 0,tmp[4],tmp[6],-1 };
cmds[pos++] = t;
}
else if (tmp[0] == 'a')
{
CMD t = { 1,tmp[4],tmp[6],-1 };
cmds[pos++] = t;
}
else
break;
}
int cpos = 0;
while (cpos < pos)
{
int index = findrela(cmds, cmds[cpos], cpos - 1);
if (cmds[cpos].type == 1)
{
int index2 = findrela(cmds, cmds[cpos], cpos - 1);
index = max(index, index2);
}
if (index == -1)
cmds[cpos].time = 0;
else
cmds[cpos].time = cmds[index].time + 1;
cpos++;
}
int maxt = 0;
for (int s = 0; s < pos; s++)
maxt = max(cmds[s].time, maxt);
printf("%d\n", maxt + 1);
}
return 0;
}