1. 程式人生 > >【leetcode】動態規劃之01揹包問題

【leetcode】動態規劃之01揹包問題

先學會手動填動態規劃的表

 後面的顏色塊值是根據前面的顏色塊值計算出來的,不懂就留言

#include<iostream>
#include<vector>
using namespace std;
int Knapsack(vector<int> weights, vector<int> values, int capacity)
{
	//獲取物品的個數
	int N = weights.size();
	//用C表示揹包最大容量
	int C = capacity;
	//維護一個二維矩陣表
	int row = N;
	int columns = capacity + 1;
	vector<vector<int>>MaxValue(row, vector<int>(columns, 0));
	//開始更新這個二維矩陣列表的值
	for (int i = 0;i < columns;i++)
	{//容量從0一次增加到capacity
		for (int j = 0;j < row;j++)
		{//從上往下,依次更新當前最優值
			if (j == 0)
			{//第一行特殊處理,容量能裝下,就取當前值。裝不下,則取值為0;
				if (i >= weights[j])
				{//當前容量能裝下第一件物品
					MaxValue[j][i] = values[j];
				}
				else
				{//當前容量不能裝下第一件物品
					MaxValue[j][i] = 0;
				}
			}
			else if (i == 0)
			{
				//因為第一列容量為0,所以也全部置為0
				MaxValue[j][i] = 0;
			}
			else 
			{//後面的值可以用來比較

				if (i < weights[j])
				{//如果容量裝不下新物品,則當前值直接取上一行當前列的值
					MaxValue[j][i] = MaxValue[j-1][i];
				}
				else
				{//比較 (裝當前物品+剩餘容量最大值) 與 (該位置上一行的值) 取最大值為當前值
					MaxValue[j][i] = values[j] + MaxValue[j - 1][i - weights[j]] > MaxValue[j - 1][i] ? values[j] + MaxValue[j - 1][i - weights[j]] : MaxValue[j - 1][i];
					////分割寫法
					//int value1 = values[j] + MaxValue[j - 1][i - weights[j]];//(裝當前物品+剩餘容量最大值)
					//int value2 = MaxValue[j - 1][i];//(該位置上一行的值)
					//MaxValue[j][i] = value1 > value2 ? value1 : value2;//取最大值為當前值
				}

			}
		}
	}
	//返回矩陣最後的值
	return MaxValue[row - 1][columns - 1];
}

int main()
{
	int w[5] = { 4, 5, 6, 2, 2 };
	int v[5] = { 6, 4, 5, 3, 6 };
	int capacity = 10;
	vector<int> weights(w, w + 5);
	vector<int> values(v, v + 5 );
	cout << Knapsack(weights, values, capacity) << endl;
	return 0;
}