0-1背包问题的动态规划求解

思路:

设value_get[i][j]为把前i个物品装入容量为j的背包所能获得的最大价值

需考虑能否装入物品i,以及是否装入物品i,递归式为:

value_get[i][j]  = max{ value_get[i-1][j], value_get[i-1][ j-weight[i] ] + value[i] } 


c语言代码如下:

/*************************************************************************
    > File Name: knapsack_dynamic.c
    > Author: arui
    > Mail: 450252722@qq.com 
    > Created Time: Wed 26 Feb 2014 01:43:14 PM CST
 ************************************************************************/

#include <stdio.h>
#include <stdlib.h>

int knapsack_dynamic(int capacity,
		            int *weight,
					int *value,
					int *choice, 
					int obj_num)
{
	int ** value_get = (int**)malloc(sizeof(int*) * (obj_num + 1));
	for(int i = 0; i <= obj_num; ++i)
	{
		value_get[i] = (int*)malloc(sizeof(int) * (capacity + 1));

	}
	//initialize
	for(int j = 0; j <= capacity; ++j)
	{
		value_get[0][j] = 0;
	}
	for(int i = 0; i <= obj_num; ++i)
	{
		value_get[i][0] = 0;
	}

	for(int i=1; i <= obj_num; ++i)
	{
		for(int j=1; j <= capacity; ++j)
		{
			value_get[i][j] = value_get[i-1][j];
			if(weight[i] <= j)
			{
				int temp_value = value_get[i-1][j-weight[i]] + value[i];
				if(temp_value > value_get[i][j])
					value_get[i][j] = temp_value;
			}
		}
	}
	//construct the choice
	int j = capacity;
	for(int i = obj_num; i > 0; --i)
	{
		if(value_get[i][j] > value_get[i-1][j])
		{
			choice[i] = 1;
			j = j - weight[i];
		}
	}
	//free the space 
	for(int i = 0; i <= obj_num; ++i)
	{
		free(value_get[i]);
	}
	free(value_get);

	return value_get[obj_num][capacity];
}

int main(int argc, char** argv)
{
	int *weight;
	int *value;
	int *choice;
	int capacity;
	int obj_num;

	freopen("test.dat","r", stdin);

	while(scanf("%d%d",&capacity, &obj_num) != EOF)
	{
		weight = (int*)malloc((obj_num + 1) * sizeof(int));
		value = (int*)malloc((obj_num + 1) * sizeof(int));
		choice = (int*)malloc((obj_num + 1) * sizeof(int));
		
		for(int i = 1; i <= obj_num; ++i)
		{
			scanf("%d", weight + i);
		}
		for(int i = 1; i <= obj_num; ++i)
		{
			scanf("%d", value + i);
		}

		int max_value = knapsack_dynamic(capacity,
				weight, value, choice, obj_num);

		printf("max_value = %d\n", max_value);
		for(int i = 1; i <= obj_num; ++i)
		{
			printf("%d", choice[i]);
		}
		printf("\n");
		
		//free the space

		free(weight);
		free(value);
		free(choice);
	}
	return 0;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值