这是个模拟题,但是由于数据量很大,不能只是单纯的模拟,但是细节的处理很重要。核心思路是每一步找出最小的时间,取整得到min.然后每一步应该是每一个任务的时间-(min-1),这样方便计时。
#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cmath>
#include <cstring>
using namespace std;
int main()
{
//freopen("in.txt","r",stdin);
double task[110],time[110],cur;
int cas,n,rest,flag,vis[110],min;
scanf("%d",&cas);
for(int i=1; i<=cas; i++)
{
scanf("%d",&n);
rest=n;
memset(time,0,sizeof(time));
min=10000009;
flag=0;
for(int j=0; j<n; j++)
{
cin>>task[j];
int a=(int)task[j];
if(task[j]-a<1e-12)
a--;
min=min<a?min:a;
}
cur=0;
while(rest)
{
memset(vis,0,sizeof(vis));
cur+=min*rest;
int minn=min;
min=10000009;
for(int j=0; j<n; j++)
{
if(task[j]<1e-12&&task[j]>-1e-12)
continue;
task[j]-=minn;
if(task[j]-1>1e-12)
{
cur++;
task[j]--;
}
else
{
cur+=task[j];
task[j]=0;
rest--;
time[j]=cur;
continue;
}
int a=(int)task[j];
if(task[j]-a<1e-12)
a--;
min=min<a?min:a;
}
}
cout<<"Case "<<i<<":"<<endl;
for(int i=0; i<n; i++)
printf("%.2lf\n",time[i]);
}
return 0;
}
下面代码是对min-1的另一种处理思路,直接减去min.
#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cmath>
#include <cstring>
#define efs 1e-6
using namespace std;
int main()
{
//freopen("in.txt","r",stdin);
double task[110],time[110],min,cur;
int cas,n,rest,flag;
scanf("%d",&cas);
for(int i=1; i<=cas; i++)
{
scanf("%d",&n);
rest=n;
memset(time,0,sizeof(time));
min=10000009;
flag=0;
for(int j=0; j<n; j++)
{
cin>>task[j];
if(task[j]<min)
min=task[j];
}
cur=0;
while(rest)
{
int a=floor(min);
cur+=a*rest;
min=10000009;
for(int j=0; j<n; j++)
{
if(task[j]>-1e-6&&task[j]<efs)
continue;
task[j]-=a;
if(task[j]>-1e-6&&task[j]<efs)
{
int temp=0;
task[j]=0;
for(int h=n-1; h>j; h--)
if((int)task[h]!=0)
temp++;
time[j]=cur-temp;
rest--;
continue;
}
}
for(int j=0; j<n; j++)
{
if(task[j]>-1e-6&&task[j]<efs)
continue;
if(task[j]-1<efs)
{
cur+=task[j];
task[j]=0;
rest--;
time[j]=cur;
}
else
{
cur++;
task[j]--;
min=min<task[j]?min:task[j];
}
}
}
cout<<"Case "<<i<<":"<<endl;
for(int i=0; i<n; i++)
printf("%.2lf\n",time[i]);
}
return 0;
}