UVA - 12589(learning vector dp)

来源:互联网 发布:java无参方法构造 编辑:程序博客网 时间:2024/05/01 10:07

这题状态很好想,而且向量按斜率降序排一下,就行了,只是不用滚动数组,就超时,也是无语了、

#include <cstdio>#include <cstring>#include <algorithm>#include <iostream>using namespace std;#define rep(i,n) for(int (i)=0;(i)<n;(i)++)#define rep1(i,x,y) for(int (i)=x;(i)<=y;(i)++)const int inf = 1e9;const int N = 55;struct point{  int x,y;  point(int x=0,int y=0):x(x),y(y){}  bool operator<(const point& rhs)const{    return rhs.x*y>=rhs.y*x;  }}a[N];int area(int h,point b){  return (b.y+h*2)*b.x;}int d[2][N][N*N],he[N]={0};int n,k;int dp(int lim){  for(int i=1;i<=n;i++) he[i]=he[i-1]+a[i].y;   for(int j=0;j<=k;j++)      for(int h=0;h<=lim;h++){            if(j==k) d[0][j][h]=0;            else d[0][j][h] = -inf;    }  int pre=0,now=1;  for(int i=n-1;i>=0;i--){    for(int j=0;j<=k;j++)      for(int h=0;h<=lim;h++){         d[now][j][h]=d[pre][j][h];         if(j<k && h+a[i+1].y<=lim)            d[now][j][h]=max(d[now][j][h],d[pre][j+1][h+a[i+1].y]+area(h,a[i+1]));    }    now^=1; pre^=1;  }  return d[pre][0][0];}int main(){    int T,kase=1;    scanf("%d",&T);    while(T--){      scanf("%d %d",&n,&k);      rep1(i,1,n)        scanf("%d %d",&a[i].x,&a[i].y);      sort(a+1,a+1+n);      int lim = 0;      for(int i=n,j=1;j<=n;i--,j++) lim+=a[i].y;      printf("Case %d: %d\n",kase++,dp(lim));    }    return 0;}/*24 33 50 22 23 04 23 50 22 23 0*/


0 0