您的位置:首页 > 其它

hdu 2059 龟兔赛跑 动规问题

2012-10-14 16:28 393 查看
首先 这个题目我并没有用动规的思想来做,自己写了个程序 手动模拟加油与不加油的情况,并在每次取得较小值,

在样本数据中演示毫无压力,但是提交的时候WA了 , 仔细看了题干条件 猜了一些测试数据,还是没错,所以不知道哪个地方错了

还麻烦能找到特殊数据证明我这个程序错误的大大多多指教,谢谢了!

源代码如下:

#include<stdio.h>

#define NUM 100

int P[NUM+10];

double calculate(int n,int c,int t,int vt1,int vt2,int l)

{

int i,cc=c;

double time=0.0;

for(i=0;i<n;i++)

{

if(i==0)

{

if(P[i]<=cc)

{

time+=(double)P[i]/vt1;

cc-=P[i];

}

else

{

time+=(double)cc/vt1+(double)(P[i]-cc)/vt2;

cc=0;

}

}

else

{

int x1=P[i]-P[i-1],x2=P[i]-P[i-1],cc1=cc,cc2=cc;

double time1=0.0,time2=0.0;

cc1=c;

time1+=t;

if(x1<=cc1)

{

time1+=(double)x1/vt1;

cc1-=x1;

}

else

{

time1+=(double)cc1/vt1+(double)(x1-cc1)/vt2;

cc1=0;

}

if(x2<=cc2)

{

time2+=(double)x2/vt1;

cc2-=x2;

}

else

{

time2+=(double)cc2/vt1+(double)(x2-cc2)/vt2;

cc2=0;

}

if(time1<time2)

{

time+=time1;

cc=cc1;

}

else

{

time+=time2;

cc=cc2;

}

}

}

if(i==n)

{

int x1=l-P[n-1],x2=l-P[n-1],cc1=cc,cc2=cc;

double time1=0.0,time2=0.0;

cc1=c;

time1+=t;

if(x1<=cc1)

{

time1+=(double)x1/vt1;

cc1-=x1;

}

else

{

time1+=(double)cc1/vt1+(double)(x1-cc1)/vt2;

cc1=0;

}

if(x2<=cc2)

{

time2+=(double)x2/vt1;

cc2-=x2;

}

else

{

time2+=(double)cc2/vt1+(double)(x2-cc2)/vt2;

cc2=0;

}

if(time1<time2)

time+=time1;

else

time+=time2;

return time;

}

}

int main()

{

int L,N,C,T,VR,VT1,VT2;

while(scanf("%d%d%d%d%d%d%d",&L,&N,&C,&T,&VR,&VT1,&VT2)!=EOF)

{

int i;

for(i=0;i<N;i++)

scanf("%d",P+i);

double t1=(double)L/VR;

double t2=calculate(N,C,T,VT1,VT2,L);

if(t1>t2)

printf("What a pity rabbit!\n");

else

printf("Good job,rabbit!\n");

}

return 0;

}

既然这个在oj上提交显示错误,那没办法了,只能选择用动规的思想来做了

f[n+2]表示每个加油站所用的最小的时间,起点和终点也算成两个加油站,在i每次到了一个点的时候,

取j从0开始到i-1的站,在每个站计算当前j到i加油站的时间,然后取值f[i]=min(f[i],f[j]+time)

子问题是f[i]肯定包含了f[j]的最小时间,用剪贴思想即可想到

该程序从表面上看是在每个点都加了油,但是其实是这样的:

i=4 j=1时,从1加油站开始加满油 跑到第四个加油站了,这个中间包含了在2 3 加油站有没有加油的情况,在每次读表的时候都取到了当前的最小值

这里面就包含了在各个站加或不加的情况了

源代码如下:

#include<stdio.h>

#define NUM 100

#define INT_MAX 999999999

int p[NUM+10];

double f[NUM+10];

int main()

{

int l,n,c,t,vr,vt1,vt2;

while(scanf("%d%d%d%d%d%d%d",&l,&n,&c,&t,&vr,&vt1,&vt2)!=EOF)

{

int i,j;

double time1;

p[0]=0;

for(i=1;i<=n;i++)

scanf("%d",p+i);

p[n+1]=l;

f[0]=0;

for(i=1;i<=n+1;i++)

f[i]=INT_MAX;

for(i=1;i<=n+1;i++)

for(j=0;j<i;j++) //动规核心算法

{

int k=p[i]-p[j];

if(k>c)

time1=(double)c/vt1+(double)(k-c)/vt2;

else

time1=(double)k/vt1;

if(j>0)

time1+=t;

if(f[i]>f[j]+time1)

f[i]=f[j]+time1;

}

if(f[n+1]>(double)l/vr)

printf("Good job,rabbit!\n");

else

printf("What a pity rabbit!\n");

}

return 0;

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: