容易想到状态方程:f[i][j] = max(f[i][j], f[child[i][k] + f[i][j - k]), 但一开始没有注意到很多细节,WA了几次之后看了discuss之后才了解:
(0)有些节点不需要留下trooper,但我们仍然需要派遣至少1个trooper去这些节点
(1)我们必须先攻克父节点才能进入子节点(必须在父节点留够充分的troopers才能进入下一个节点)
(2)进入子节点的时候我们必须携带至少1个的troopers,尽管一些节点并不需要留下trooper
下面是标准的读入、建树、DP过程:
#include <cstdio>
#include <cstring>
#include <vector>
#include <algorithm>
using namespace std;
int N, M;
struct Node{
int cost, gain;
vector<int> children;
} arr[101];//tree structure
int gain[101][101];//best[i][j] is for subtree with root being node i,