fixingthegreatwalluva-1336(区间dp)

yijiull yijiull     2022-09-16     605

关键词:

Fixing the Great Wall

 UVA - 1336

题意:修长城,初始位置为fp,n个点要修,初始每个点修缮费用为ci,单位时间增加费用di,问最少费用。

区间dp

和送外卖那个差不多~

有一个细节,输入不加!=EOF的话会超时(虽然题目说了以00结束)

技术分享
 1 #include <cstdio>
 2 #include <bits/stdc++.h>
 3 using namespace std;
 4 const int maxn=1005;
 5 struct node
 6 {
 7     int pos,c,d;
 8     node(int pos=0,int c=0,int d=0):pos(pos),c(c),d(d){}
 9     bool operator <(const node &x) const
10     {
11         return pos<x.pos;
12     }
13 }p[maxn];
14 int sum[maxn];
15 double dp[maxn][maxn][2];
16 
17 int main()
18 {
19      int n,v,fp;
20      while(scanf("%d%d%d",&n,&v,&fp)!=EOF&&(n||v||fp))
21      {
22         for(int i=0;i<n;i++)
23             scanf("%d%d%d",&p[i].pos,&p[i].c,&p[i].d);
24         p[n].pos=fp;p[n].c=0;p[n].d=0;
25         sort(p,p+n+1);
26         int w=lower_bound(p,p+n+1,node(fp,0,0))-p;
27         sum[0]=p[0].d;
28         for(int i=1;i<=n;i++) sum[i]=sum[i-1]+p[i].d;
29         //memset(dp,0x3f3f3f3f,sizeof(dp));
30         for(int i=0;i<=n;i++)
31             for(int j=i;j<=n;j++) dp[i][j][0]=dp[i][j][1]=0x3f3f3f3f;
32         dp[w][w][0]=dp[w][w][1]=0;
33         for(int i=w;i>=0;i--)
34             for(int j=w;j<=n;j++)
35         {
36             double ss=sum[i-1]+sum[n]-sum[j];
37             if(i!=0)  //往左
38             {
39                 //从左到左
40                 double t=1.0*(p[i].pos-p[i-1].pos)/v;
41                 dp[i-1][j][0]=min(dp[i-1][j][0],dp[i][j][0]+p[i-1].c+t*ss);
42                 //从右到左
43                 t=1.0*(p[j].pos-p[i-1].pos)/v;
44                 dp[i-1][j][0]=min(dp[i-1][j][0],dp[i][j][1]+p[i-1].c+t*ss);
45             }
46             if(j!=n) //往右
47             {
48                 //从右到右
49                 double t=1.0*(p[j+1].pos-p[j].pos)/v;
50                 dp[i][j+1][1]=min(dp[i][j+1][1],dp[i][j][1]+p[j+1].c+ss*t);
51                 //从左到右
52                 t=1.0*(p[j+1].pos-p[i].pos)/v;
53                 dp[i][j+1][1]=min(dp[i][j+1][1],dp[i][j][0]+p[j+1].c+ss*t);
54             }
55         }
56         int ans=min(dp[0][n][0],dp[0][n][1]);
57         printf("%d
",ans);
58      }
59      return 0;
60 }
View Code