标签归档:装箱问题

装箱问题

描述 Description
有一个箱子容量为v(正整数,o≤v≤20000),同时有n个物品(o≤n≤30),每个物品有一个体积 (正整数)。要求从 n 个物品中,任取若千个装入箱内,使箱子的剩余空间为最小。

输入格式 Input Format
第一行,一个整数,表示箱子容量;
第二行,一个整数,表示有n个物品;
接下来n行,分别表示这n个物品的各自体积。

输出格式 Output Format
一个整数,表示箱子剩余空间。

样例输入 Sample Input
24
6
8
3
12
7
9
7

样例输出 Sample Output

0
算法描述:动态规划
一个简单的动态规划问题-01背包
f[i][j]=max{f[i-1][j],f[i-1][j-g[i]+g[i](j-g[i]>=0)}
f[0][j]=0
逐行递推答案即为(V-f[n][v])
我没有用这种方法。二维太复杂了,写了个一维的。就是一个一个的放,放在以前存在的情况上,然后相加,注意这里最重要的一点是要从后面往前面找那个存在的。
【代码】

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
#include <stdio.h>
#include <string.h>
int main()
{
	int a[100], v, n, i, j, k, b[20001], t;
	scanf("%d%d", &v, &n);
	for (i = 1; i <= n; i++)
		scanf("%d", &a[i]);
	memset(b, 0, sizeof(b));
	k = 0;
	b[0] = 1;
	for (i = 1; i <= n; i++)
	{
		t = k;
		for (j = k; j >= 0; j--)//切记一定要从后面往前面找。                   
			if (b[j] == 1 && j + a[i] <= v)                                                                     
			{
				b[j + a[i]] = 1;
				if (j + a[i] > t)
					t = j + a[i];
			}
		k = t;
	}
	printf("%d\n", v - k);
	return 0;
}