BZOJ 1017 魔兽地图

Description

DotR (Defense of the Robots) Allstars是一个风靡全球的魔兽地图,他的规则简单与同样流行的地图DotA (Defense of the Ancients) Allstars。DotR里面的英雄只有一个属性——力量。他们需要购买装备来提升自己的力量值,每件装备都可以使佩戴它的英雄的力量值提高固定的点数,所以英雄的力量值等于它购买的所有装备的力量值之和。装备分为基本装备和高级装备两种。基本装备可以直接从商店里面用金币购买,而高级装备需要用基本装备或者较低级的高级装备来合成,合成不需要附加的金币。装备的合成路线可以用一棵树来表示。比如,Sange and Yasha的合成需要Sange, Yasha和Sange and Yasha Recipe Scroll三样物品。其中Sange又要用Ogre Axe, Belt of Giant Strength 和 Sange Recipe Scroll合成。每件基本装备都有数量限制,这限制了你不能无限制地合成某些性价比很高的装备。现在,英雄Spectre有M个金币,他想用这些钱购买装备使自己的力量值尽量高。你能帮帮他吗?他会教你魔法Haunt(幽灵附体)作为回报的。

Input

输入文件第一行包含两个整数,N (1 <= n <= 51) 和 m (0 <= m <= 2,000)。分别表示装备的种类数和金币数。装备用1到N的整数编号。接下来的N行,按照装备1到装备n的顺序,每行描述一种装备。每一行的第一个正整数表示这个装备贡献的力量值。接下来的非空字符表示这种装备是基本装备还是高级装备,A表示高级装备,B表示基本装备。如果是基本装备,紧接着的两个正整数分别表示它的单价(单位为金币)和数量限制(不超过100)。如果是高级装备,后面紧跟着一个正整数C,表示这个高级装备需要C种低级装备。后面的2C个数,依次描述某个低级装备的种类和需要的个数。

Output

第一行包含一个整数S,表示最多可以提升多少点力量值。

Sample Input

10 59
5 A 3 6 1 9 2 10 1
1 B 5 3
1 B 4 3
1 B 2 3
8 A 3 2 1 3 1 7 1
1 B 5 3
5 B 3 3
15 A 3 1 1 5 1 4 1
1 B 3 5
1 B 4 3

Sample Output

33

HINT

Source

很明显的树形dp。开始我不会d,所以准备照着hzwer的copy,后来弄懂了树p的真谛,天黑都不怕了。

树p一般都要开dp两次,通过第一个dp结果来dp第二个,再根据第二个来更新第一个(等于第二个dp只是个桥梁吧)。

像这一题,f[i][j][k]表示i物品贡献给父亲j个花了k的最大力量,通过g数组来完成转移。g[i][k]表示考虑前i个儿子,花j的最大费用,单其实只要一维就够了,因为它可以滚动使用。

如果实在是听不的话,看代码就行了。我就是看代码才理解的。

  1 #include<iostream>
  2 #include<cstring>
  3 #include<vector>
  4 #include<cstdio>
  5 #include<algorithm>
  6 #include<cstdlib>
  7 using namespace std;
  8
  9 #define inf (1<<29)
 10 #define maxn 60
 11 #define maxm 2010
 12 #define maxl 110
 13 int n,m,con[maxn],pri[maxn],lim[maxn];
 14 int f[maxn][maxl][maxm],g[maxm],root,ans;
 15 bool bas[maxn];
 16 vector < pair <int,int> > need[maxn];
 17
 18 inline int Max(int a,int b) { if (a > b) return a; return b; }
 19
 20 inline int Min(int a,int b) { if (a < b) return a; return b; }
 21
 22 inline int getint()
 23 {
 24     int x=0,f=1;char ch=getchar();
 25     while(ch<‘0‘||ch>‘9‘){if(ch==‘-‘)f=-1;ch=getchar();}
 26     while(ch>=‘0‘&&ch<=‘9‘){x=x*10+ch-‘0‘;ch=getchar();}
 27     return x*f;
 28 }
 29
 30 inline void read()
 31 {
 32     for (int i = 1;i <= n;++i)
 33     {
 34         con[i] = getint();
 35         char opt = getchar();
 36         if (opt == ‘A‘)
 37         {
 38             int nn = getint();
 39             for (int j = 1;j <= nn;++j)
 40             {
 41                 int a = getint(),b = getint();
 42                 need[i].push_back(make_pair(a,b));
 43                 bas[a] = true;
 44             }
 45             lim[i] = inf;
 46         }
 47         else pri[i] = getint(),lim[i] = getint();
 48     }
 49     for (int i = 1;i <= n;++i)
 50         if (!bas[i]) { root = i; break; }
 51 }
 52
 53 inline void dp(int now)
 54 {
 55     if (need[now].size() == 0)
 56     {
 57         lim[now] = Min(lim[now],m/pri[now]);
 58         for (int i = 0;i <= lim[now];++i)
 59             for (int j = i;j <= lim[now];++j)
 60                 f[now][i][j*pri[now]] = (j-i)*con[now];
 61         return;
 62     }
 63     lim[now] = inf; int nn = need[now].size();
 64     for (int i = 0;i < nn;++i)
 65         dp(need[now][i].first),lim[now] = Min(lim[now],lim[need[now][i].first]/need[now][i].second);
 66     for (int i = 0;i <= lim[now];++i) f[now][i][0] = 0;
 67     for (int i = 0;i < nn;++i)
 68         for (int j = 0;j <= lim[now];++j)
 69         {
 70             memcpy(g,f[now][j],sizeof(g));
 71             memset(f[now][j],-1,sizeof(g));
 72             for (int k = m;k >= 0;--k)
 73             {
 74                 for (int r = k;r >= 0; --r)
 75                     if (g[k - r] != -1&&f[need[now][i].first][j*need[now][i].second][r] != -1)
 76                     {
 77                         f[now][j][k] = Max(f[now][j][k],g[k-r]+f[need[now][i].first][j*need[now][i].second][r]);
 78                         ans = Max(ans,f[now][j][k]);
 79                     }
 80             }
 81         }
 82     for (int i = 0;i <= lim[now];++i)
 83         for (int j = i;j <= lim[now];++j)
 84             for (int k = 0;k <= m;++k)
 85             {
 86                 if (f[now][j][k] == -1) continue;
 87                 f[now][i][k] = Max(f[now][i][k],f[now][j][k] + (j-i)*con[now]),ans = Max(ans,f[now][i][k]);
 88             }
 89 }
 90
 91 int main()
 92 {
 93     freopen("1017.in","r",stdin);
 94     freopen("1017.out","w",stdout);
 95     memset(f,-1,sizeof(f));
 96     scanf("%d %d",&n,&m);
 97     read();
 98     dp(root);
 99     printf("%d",ans);
100     fclose(stdin); fclose(stdout);
101     return 0;
102 }

时间: 2024-10-03 15:01:28

BZOJ 1017 魔兽地图的相关文章

BZOJ 1017 魔兽地图DotR(树形DP)

题意:有两类装备,高级装备A和基础装备B.现在有m的钱.每种B有一个单价和可以购买的数量上限.每个Ai可以由Ci种其他物品合成,给出Ci种其他物品每种需要的数量.每个装备有一个贡献值.求最大的贡献值.已知物品的合成路线是一个严格的树模型.即有一种物品不会合成其他任意物品,其余物品都会仅仅可用作合成另外一种物品 思路:f[i][j][k],代表第i个物品,花费了j,向上提供k个i物品. 1 #include<algorithm> 2 #include<cstdio> 3 #inclu

BZOJ [JSOI2008]魔兽地图DotR

1017: [JSOI2008]魔兽地图DotR Time Limit: 30 Sec  Memory Limit: 162 MBSubmit: 1243  Solved: 532[Submit][Status][Discuss] Description DotR (Defense of the Robots) Allstars是一个风靡全球的魔兽地图,他的规则简单与同样流行的地图DotA (Defense of the Ancients) Allstars.DotR里面的英雄只有一个属性——力

【BZOJ 1017】 [JSOI2008]魔兽地图DotR

1017: [JSOI2008]魔兽地图DotR Time Limit: 30 Sec  Memory Limit: 162 MB Submit: 1069  Solved: 433 [Submit][Status] Description DotR (Defense of the Robots) Allstars是一个风靡全球的魔兽地图,他的规则简单与同样流行的地图DotA (Defense of the Ancients) Allstars.DotR里面的英雄只有一个属性--力量.他们需要购

bzoj 1017[JSOI2008]魔兽地图DotR - 树形dp

1017: [JSOI2008]魔兽地图DotR Time Limit: 30 Sec  Memory Limit: 162 MB Description DotR (Defense of the Robots) Allstars是一个风靡全球的魔兽地图,他的规则简单与同样流行的地图DotA (Defense of the Ancients) Allstars.DotR里面的英雄只有一个属性--力量.他们需要购买装备来提升自己的力量值,每件装备都可以使佩戴它的英雄的力量值提高固定的点数,所以英雄

[BZOJ 1017][JSOI2008]魔兽地图DotR(树形Dp)

Description DotR (Defense of the Robots) Allstars是一个风靡全球的魔兽地图,他的规则简单与同样流行的地图DotA (Defense of the Ancients) Allstars.DotR里面的英雄只有一个属性——力量.他们需要购买装备来提升自己的 力量值,每件装备都可以使佩戴它的英雄的力量值提高固定的点数,所以英雄的力量值等于它购买的所有装备的力 量值之和.装备分为基本装备和高级装备两种.基本装备可以直接从商店里面用金币购买,而高级装备需要用

[JSOI2008][BZOJ1017] 魔兽地图DotR|树形动规

1017: [JSOI2008]魔兽地图DotR Time Limit: 30 Sec  Memory Limit: 162 MBSubmit: 1254  Solved: 537[Submit][Status][Discuss] Description DotR (Defense of the Robots) Allstars是一个风靡全球的魔兽地图,他的规则简单与同样流行的地图DotA (Defense of the Ancients) Allstars.DotR里面的英雄只有一个属性——力

BZOJ 1017--魔兽地图(树形DP&amp;完全背包)

1017: [JSOI2008]魔兽地图DotR Time Limit: 30 Sec  Memory Limit: 162 MBSubmit: 2674  Solved: 1041[Submit][Status][Discuss] Description DotR (Defense of the Robots) Allstars是一个风靡全球的魔兽地图,他的规则简单与同样流行的地图DotA (Defense of the Ancients) Allstars.DotR里面的英雄只有一个属性——

BZOJ1017: [JSOI2008]魔兽地图DotR

传送门 设$f[i][j][k]$表示对于第$i$个点,向父节点贡献$j$个已合成的装备,花费了$k$的代价,最多获得的力量值. 单纯的$f[i][j][k]$是很难转移的,主要原因是无法维护和其他儿子的关系.所以对于每个节点再搞一个$g[i][j]$表示当前点的前$i$个儿子花费为$k$可以获得的最大的力量值. 然后肯定要先更新$g[][]$再以$g[][]$来更新$f[][][]$. 列出$g[i][j]$的状态转移方程就是: $g[cnt][k]=max \{ f[son][tol \ti

【百度地图API】如何制作一张魔兽地图!!——CS地图也可以,哈哈哈

原文:[百度地图API]如何制作一张魔兽地图!!--CS地图也可以,哈哈哈 摘要: 你玩魔兽不?你知道如何做一张魔兽地图不?! 快来看此文吧! --------------------------------------------- 一.制作魔兽地图的准备工作 其实,你只需要准备一些地图的瓦片图,就可以了. 用切片工具,把一张完整的图片(最好大一些,清楚一些),切成小片.(下周我贴这个工具的下载链接出来.留个悬念,哈哈.) 正式公布切图工具链接: http://openapi.baidu.co