题目大意:
给定一个形式的天枰,天枰上远离中点的不同距离拥有钩子。给定各种重量砝码,问必须悬挂所有砝码的前提下,维持天枰平衡的挂法数为多少?
暴力尝试的枚举量惊人,显然即使天枰当前不平衡,但它的“不平衡度”是可以利用的。关键是如何设计DP状态。普遍的做法是以i个物品为阶段,计算悬挂到第i个物品时,当前平衡度达到v的方法总数。易得 -7500<=v<=7500; dp[i][v]=∑dp[i-1][v-hoox[j]*w[i]] → dp[i][v+inf]=∑dp[i-1][v-hoox[j]*w[i]+inf]。常数 inf 仅为保证数组下标不为负。我们明显发现它在形式上类似于背包问题,等价于在v容背包中,尝试放入重量为hoox[j]*w[i]的物品,换取收益一种方法。
容易理解,初始解 dp[0][0+inf]=1,目标解 dp[m][0+inf] 。
类比:
http://acm.ustc.edu.cn/ustcoj/problem.php?id=1116
DD牛 << 背包九讲 >>
1#include<cstdio>
2#include<cstring>
3#define G 21
4#define N 21
5#define inf 7500
6
7int dp[G][inf+inf+1];
8int w[G],h[N];
9
10int main(){
11 int n,m,i,j,v;
12 while(scanf("%d%d",&n,&m)!=EOF){
13 for(i=0;i<n;i++) scanf("%d",&h[i]);
14 for(i=1;i<=m;i++) scanf("%d",&w[i]);
15
16 memset(dp,0,sizeof(dp));
17 dp[0][0+inf]=1;
18
19 for(i=1;i<=m;i++)
20 for(v=-1*inf;v<=inf;v++)
21 for(j=0;j<n;j++)
22 if( v-h[j]*w[i]+inf+1 )
23 dp[i][v+inf]+=dp[i-1][v-h[j]*w[i]+inf];
24
25 printf("%d\n",dp[m][0+inf]);
26 }
27 return 0;
28}
29