dp+斜率优化~~
http://acm.hdu.edu.cn/showproblem.php?pid=3480
View Code
1 # include<stdio.h> 2 # include<string.h> 3 # include<stdlib.h> 4 # define N 10005 5 int a[N],s[N],k; 6 int dp[2][N]; 7 int cmp(const void *a,const void *b) 8 { 9 return *(int *)a -*(int *)b; 10 } 11 int K(int i1,int i2,int j) 12 { 13 int x1,y1,x2,y2,x0,y0; 14 y1=dp[(k-1)%2][i1]+a[i1+1]*a[i1+1]; 15 x1=a[i1+1]; 16 y2=dp[(k-1)%2][i2]+a[i2+1]*a[i2+1]; 17 x2=a[i2+1]; 18 y0=dp[(k-1)%2][j]+a[j+1]*a[j+1]; 19 x0=a[j+1]; 20 return (x2-x1)*(y0-y2)-(x0-x2)*(y2-y1); 21 } 22 int G(int j,int i) 23 { 24 return dp[(k-1)%2][j]+(a[j+1]-a[i])*(a[j+1]-a[i]); 25 } 26 int main() 27 { 28 int i,j,n,m; 29 int t,ncase; 30 int f,end,mm; 31 scanf("%d",&ncase); 32 for(t=1;t<=ncase;t++) 33 { 34 scanf("%d%d",&n,&m); 35 for(i=1;i<=n;i++) 36 scanf("%d",&a[i]); 37 printf("Case %d: ",t); 38 if(n<=m) {printf("0\n");continue;} 39 memset(dp,0,sizeof(dp)); 40 qsort(a+1,n,sizeof(a[1]),cmp); 41 mm=1; 42 for(i=2;i<=n;i++) 43 if(a[i]!=a[i-1]) a[++mm]=a[i]; 44 n=mm; 45 for(i=1;i<=n;i++) 46 dp[1][i]=(a[i]-a[1])*(a[i]-a[1]); 47 for(k=2;k<=m;k++) 48 { 49 f=1; 50 end=0; 51 for(i=k;i<=n;i++) 52 { 53 j=i-1; 54 while(end-1>=f && K(s[end-1],s[end],j)<=0) end--; 55 s[++end]=j; 56 while(f<end && G(s[f],i)>=G(s[f+1],i)) f++; 57 dp[k%2][i]=G(s[f],i); 58 } 59 } 60 printf("%d\n",dp[m%2][n]); 61 } 62 return 0; 63 }