[]ナップザック問題動的プログラミング - 例分析

バリアント複数のナップザック問題

強化のための機器

タイトル説明
オンラインゲームは、戦闘能力の役割を強化するための装置を持ち上げるための一般的な方法です。今、あなたは、ゲームの開発に関与し、この機能を持って、チームは戦闘能力と消費する必要性を高めることができるコインの枚数を強化するために各機器を設計しています。強化、合理的なシステムを設計するために、我々はいくつかの強化シミュレーションテストを行うことを決めた、とあなたは、シミュレーションプログラムの開発者になりました。あるnは同時に着用することができます機器の部品は、機器の私の作品のために、j番目の機器を強化するのi番目の要素のために、最大でマイル回を強化することができたと、FIJとコインを消費するのgijの必要性の戦闘力が増加します。今データは、すべての機器を与えている、と戦闘力の最大数を求めているが所有するコインの初期の数を増加させることができます。
入力説明:
入力ファイルT整数正の最初の行は、テストデータのセットを表します。
そして、データのTセットがあります。各整数の最初の二つの行為のデータの集合NおよびSは、それぞれ、機器の数を表し、コインの数が最初に持っています。n行続いて、各ラインは、最初の行のそれぞれは、機器の名前を表す文字列である機器を表し、MIは機器の数を表す第2の非負整数は、ほとんどが2続いて強化することができます* MI戦闘力を強化し、金の消費量の数を増加させるそれぞれを表す非負整数。

データ範囲:
すべてのデータファイルについて、1 <= T <= 10 。機器の名前の最大長は、以上32文字、小文字の英字または数字です。各機器は、ほとんどの場合、MI 0 <= MI <= 3を補強しました。すべての戦闘力値と金貨の数以上、10,000,000非負の整数。
;その中にデータの20%、機器1 <= N <= 5を満足する数の
データの別の30%、機器1 <= N <= 10を満たす数、
データの別の30%、数満たす装置1 <= N <= 16;
データの最後の残りの20%、1 <= N <= 20を満たす機器番号。

唯一最大の戦闘力を達成することができていることを保証するために、データの集中プログラム。

説明出力:
各テストデータについて、最初の整数の挙動は、ほとんどの昇降戦闘能力を表します。形で、これを達成するための戦闘力を回数を強化するために各機器を表すそれぞれ、n行に続く「数+名を強化するための機器。」順次データと一致するように入力装置を出力します。より詳細には、サンプル出力の形式を指します。

入力例:
3
。4 100
ヘルム,. 1 20は30のである
手袋1つの30 40。
ブーツ1 10 10。
ソード1 50 50。
5〜10。
アイテム1 0
アイテム2 1 10000 100。
ITEM3 1 10 10。
ITEM4 3 1 0 2 1 3 2。
ITEM5 3 0 4. 1. 1. 5. 1。
256 6
、1×12 43 35 2 58である
2×88 31 54 34は2である
3×2 10 15 55 43である
19 19 2 32 54である。4X
。5X 1 15 45 2 84
6×99 12 2 40 19であります

出力例:
90
ヘルム、+ 0
。手袋+ 1
。ブーツ+ 1
。剣+ 1
12である
アイテム1 + 0
アイテム2 + 0
ITEM3 + 0
ITEM4 + 3。
ITEM5 + 3。
418
1×+ 0
2X + 2
3X + 1。
4X + 2
5X + 1。
6X + 2

#include <iostream>
#include <string>
#include <vector>
#include <algorithm>
using namespace std;

//dp方程
const int max_n = 20 + 5;
const int max_s = 100 + 10;
struct Equipment {
	string name;
	int mi;
	vector<int> fij; //战力
	vector<int> gij; //金币
};

int main()
{
	int T;
	cin >> T;
	for (int c = 0; c < T; c++)
	{
		int n, s;
		cin >> n >> s;

		vector<Equipment> items(n+1); //n个装备

                //注意这里用的是i=1,因为我们希望i就代表第i个装备,0用来初始化dp中的0位置

		for (int i = 1; i <= n; i++)
		{
			cin >> items[i].name >> items[i].mi;
			for (int j = 0; j < items[i].mi; j++)
			{
				int fij, gij;
				cin >> fij >> gij;
				items[i].fij.push_back(fij);
				items[i].gij.push_back(gij);
			}
		}

		//输入完成

		int dp[max_n][max_s] = { 0 };
		int result[max_n][3] = { 0 };
                  
		for (int i = 1; i <= n; i++) //每个装备,注意这里也是i=1,i<=n
		{
			for (int j = s; j > 0; j--)
			{
				for (int k = 0; k < items[i].mi; k++)
				{
                                        int k_f = 0;//升级K次得到的战力
					int k_g = 0; //升级K次用掉的金币					

					for (int n = 0; n <= k; n++)
					{
						k_f += items[i].fij[n];
						k_g += items[i].gij[n];
					}

					if (j - k_g >= 0)
					{
                                               dp[i][j] = max(dp[i][j], dp[i - 1][j - k_g] + k_f);
					}
				}
			}
		}
		for (int i = 1; i <= n; i++)
		{
			for (int j = 1; j < s; j++)
			{
				cout << dp[i][j]<<"  ";
			}
			cout << dp[i][s]<<endl;
		}
	}
}

このDPの内部には、解決すべき問題は、(これらの項目を選択し、問題が一時停止)が、それらの出力をアップグレードする方法をされている
建設--- ----------------- ------------------

おすすめ

転載: www.cnblogs.com/EvansPudding/p/12615140.html