POJ 1837 Balance
解题思路:DP
g[i]表示第i个砝码的重量,c[j]表示第j个点的坐标,opt[i][k]表示加了i个砝码,力矩之和为k的方法数
DP公式为(考虑到力矩为负,因此需要做偏移):
opt[i+1][k+g[i]*c[j]+=opt[i][k]
第i次迭代只于i-1次有关,因此可以缩减为二维数组
NULL
#include <iostream>
using namespace std;
#define MID 4875
#define MAXN 9751
int main()
{
int i,j,k,m,n,t,*x, *y,*z,c[20],g[20],a[MAXN],b[MAXN];
scanf("%d %d", &m, &n);
for(i=0;i<m;i++)scanf("%d", &c[i]);
for(i=0;i<n;i++)scanf("%d", &g[i]);
memset(a, 0, sizeof(a));
a[MID]=1,x=a,y=b;
for(i=0;i<n;i++)
{
for(j=0;j<MAXN;j++)y[j]=0;
for(j=0;j<m;j++)
for(t=g[i]*c[j],k=0;k<MAXN;k++)
if(x[k])y[k+t]+=x[k];
z=x,x=y,y=z;
}
printf("%d\n",x[MID]);
return 0;
}