码迷,mamicode.com
首页 > 其他好文 > 详细

[usaco jan 09] 气象牛 baric [dp]

时间:2018-02-21 19:40:28      阅读:135      评论:0      收藏:0      [点我收藏+]

标签:algorithm   fine   传送门   ring   target   cstring   +=   cto   turn   

题面:

传送门

思路:

题意有点绕,实际上就是给你一个计算规则,让你取最少的元素,通过这个计算方式,得到一个小于指定误差上限的结果

这个规则分为三个部分,这里分别用pre,sum,suf表示

因为给定的元素个数(天数)很少,可以使用O(n^3)算法,因此考虑使用经过了预处理的dp解决问题

具体地,设dp[i][j]表示前i个元素使用了j个且一定取用了第i个时可能达到的最小误差值

预处理:pre[i]表示通过第一种计算方式得到的,第一个元素取第i个时得到的误差

suf[i]同理,为第三种计算方式

sum[i][j]则表示取了i和j且不取中间的元素时,中间的元素产生的误差

这样dp[i][1]=pre[i],dp[i][j]=dp[k][j-1]+sum[k][i](k=1...i-1),然后用dp[i][j]+suf[j]更新答案即可

Code:

 1 #include<iostream>
 2 #include<vector>
 3 #include<cstring>
 4 #include<cstdio>
 5 #include<algorithm>
 6 #define inf 0x7fffffff/2
 7 using namespace std;
 8 int n,m,a[110];
 9 int dp[110][110]; 
10 //dp[i][j]: prefix 1-i,chosen j
11 int pre[110],suf[110],sum[110][110];
12 int abs(int k){
13     if(k>=0) return k;
14     else return -k;
15 }
16 int main(){
17     freopen("baric.in","r",stdin);
18     freopen("baric.out","w",stdout);
19     int i,j,k,tmp1,tmp2,t,l;
20     scanf("%d%d",&n,&m);
21     int ans=m,anss=n;
22     for(i=1;i<=n;i++){
23         scanf("%d",&a[i]);
24         dp[i][1]=0;
25     } 
26     for(i=1;i<=n-2;i++){
27         for(j=i+2;j<=n;j++){
28             for(k=i+1;k<j;k++){
29                 sum[i][j]+=abs((a[k]<<1)-a[i]-a[j]);
30             }
31         }
32     }
33     for(i=1;i<=n;i++){
34         for(j=1;j<i;j++) pre[i]+=abs(a[i]-a[j])<<1;
35         dp[i][1]=pre[i];
36         for(j=n;j>i;j--) suf[i]+=abs(a[i]-a[j])<<1;
37     }
38     for(i=2;i<=n;i++){
39         for(j=2;j<=i;j++){
40             dp[i][j]=inf/2;
41             for(k=1;k<i;k++) dp[i][j]=min(dp[i][j],dp[k][j-1]+sum[k][i]);
42             if(dp[i][j]+suf[i]<m){
43                 if(j<ans) ans=j,anss=dp[i][j]+suf[i];
44                 else if(j==ans&&dp[i][j]+suf[i]<anss) anss=dp[i][j]+suf[i];
45             }
46         }
47     }
48     printf("%d %d",ans,anss);
49 } 

 

[usaco jan 09] 气象牛 baric [dp]

标签:algorithm   fine   传送门   ring   target   cstring   +=   cto   turn   

原文地址:https://www.cnblogs.com/dedicatus545/p/8457084.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!