hdu 1421 搬寝室(dp)

题目:http://acm.hdu.edu.cn/showproblem.php?pid=1421

思路:d[i][j] 表示前i 个,k对的最小值。

这个题还是不太好想状态方程,初始化以后,还要分一下情况。。

 1 #include <iostream>
 2 #include <cstdio>
 3 #include <cstring>
 4 #include <cstdlib>
 5 #include <algorithm>
 6 using namespace std;
 7 const int maxn = 2000+10;
 8 const int maxm = 1000+10;
 9 const int INF = 1<<28;
10 
11 int d[maxn][maxm];
12 int a[maxn];
13 int _min(int x, int y)
14 {
15     return x>y?y:x;
16 }
17 int main()
18 {
19     int n, k, i, j;
20     while(~scanf("%d%d", &n, &k))
21     {
22         for(i = 1; i <= n; i++)
23         scanf("%d", &a[i]);
24         sort(a+1, a+n+1);
25         for(i = 0; i < maxn; i++)
26         d[i][0] = 0;
27 
28         for(i = 2; i <= n; i++)
29         for(j = 1; j*2 <= i; j++)
30         {
31             if(j*2 <= i-1)
32             d[i][j] = _min(d[i-1][j], d[i-2][j-1]+(a[i]-a[i-1])*(a[i]-a[i-1]));  //一般情况下,求新增加一个 和以前的比较
33             else
34             d[i][j] = d[i-2][j-1]+(a[i]-a[i-1])*(a[i]-a[i-1]);   //当i为偶数情况时,且j达到最大的时候
35         }
36         printf("%d\n", d[n][k]);
37     }
38     return 0;
39 }

 

posted @ 2014-03-03 21:08  水门  阅读(187)  评论(0编辑  收藏  举报