POJ 1155
很久以前做的树形DP题,今天再遇到时,竟然不会了,所以写写。。
设数组:
prf[MAX][MAX],cost[MAX],sum[MAX]。分别表示,在第i个结点为根的子树内的情况下,若有j个用户申请看电视,所能得到的最大费用。cost表示传送到i点时所花的费用,而sum表示当前结点为根的子树内已访问的叶子结点的个数(即用户)。
void dfs(int v,int fa){
if(T[v].size()>){
for(int i=;i<T[v].size();i++){
dfs(T[v][i],v);
}
}
if(T[v].size()==)
sum[v]=;
sum[fa]+=sum[v];
prf[fa][]=;
for(int i=sum[fa];i>;i--){
for(int j=sum[v];j>;j--){
if(prf[fa][i-j]!=-INF&&prf[v][j]!=-INF)
prf[fa][i]=max(prf[fa][i],prf[fa][i-j]+prf[v][j]-cost[v]);
}
}
}
使用深搜,再运用背包来解决。
for(int i=sum[fa];i>0;i--){
for(int j=sum[v];j>0;j--){
if(prf[fa][i-j]!=-INF&&prf[v][j]!=-INF)
prf[fa][i]=max(prf[fa][i],prf[fa][i-j]+prf[v][j]-cost[v])
}
}
枚举父结点当前已访问的用户数,再枚举当前结点子树内该问了的用户数,若要在父结点的状态中加入j个当前结点有用户,则
prf[fa][i]=max(prf[fa][i],prf[fa][i-j]+prf[v][j]-cost[v])。这是拿加入j个用户后与当前i个用户的费用的比较。
前提条件时if(prf[fa][i-j]!=-INF&&prf[v][j]!=-INF),因为要在状态存在的情况下才能进行。
#include <iostream>
#include <vector> const int maxn=;
const int INF=;
using namespace std;
int n,m;
int prf[maxn][maxn];
int cost[maxn];
int sum[maxn]; vector<int>T[maxn]; void init(){
for(int i=;i<=n;i++)
for(int j=;j<=m;j++)
prf[i][j]=-INF;
memset(cost,,sizeof(cost));
memset(sum,,sizeof(sum));
for(int i=;i<=n;i++)
T[i].clear();
}
int max(int a,int b){
if(a<b)
return b;
return a;
}
void dfs(int v,int fa){
if(T[v].size()>){
for(int i=;i<T[v].size();i++){
dfs(T[v][i],v);
}
}
if(T[v].size()==)
sum[v]=;
sum[fa]+=sum[v];
prf[fa][]=;
for(int i=sum[fa];i>;i--){
for(int j=sum[v];j>;j--){
if(prf[fa][i-j]!=-INF&&prf[v][j]!=-INF)
prf[fa][i]=max(prf[fa][i],prf[fa][i-j]+prf[v][j]-cost[v]);
}
}
} int main(){
while(~scanf("%d%d", &n, &m))
{
init();
int t=,c,k,y;
T[].push_back();
while((++t)<=n-m){
scanf("%d",&k);
for(int i=;i<=k;i++){
scanf("%d%d",&y,&c);
T[t].push_back(y);
cost[y]=c;
}
}
for(k=n-m+;k<=n;k++){
scanf("%d",&c);
prf[k][]=c;
prf[k][]=;
}
dfs(,);
for(int i=m;i>=;i--)
if(prf[][i]>=){
printf("%d\n",i);
break;
}
}
return ;
}
POJ 1155的更多相关文章
- POJ 1155 树形背包(DP) TELE
题目链接: POJ 1155 TELE 分析: 用dp[i][j]表示在结点i下最j个用户公司的收益, 做为背包处理. dp[cnt][i+j] = max( dp[cnt][i+j ...
- poj 1155 输入输出问题
http://acm.hust.edu.cn/vjudge/problem/16417 重做了一遍poj 1155 题目大意:给定一棵树,1为根结点表示电视台,有m个叶子节点表示客户,有n-m-1个中 ...
- POJ 1155 (树形DP+背包+优化)
题目链接: http://poj.org/problem?id=1155 题目大意:电视台转播节目.对于每个根,其子结点可能是用户,也可能是中转站.但是用户肯定是叶子结点.传到中转站或是用户都要花钱, ...
- [POJ 1155] TELE (树形dp)
题目链接:http://poj.org/problem?id=1155 题目大意:电视台要广播电视节目,要经过中转机构,到观众.从电视台到中转商到观众是一个树形结构,经过一条边需要支付成本.现在给你每 ...
- POJ 1155 TELE 背包型树形DP 经典题
由电视台,中转站,和用户的电视组成的体系刚好是一棵树 n个节点,编号分别为1~n,1是电视台中心,2~n-m是中转站,n-m+1~n是用户,1为root 现在节点1准备转播一场比赛,已知从一个节点传送 ...
- [POJ 1155] TELE
TELE Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 3787 Accepted: 2007 Description ...
- POJ 1155 - TELE 树型DP(泛化背包转移)..
dp[x][y]代表以x为根的子树..连接了y个终端用户(叶子)..所能获得的最大收益... dp[x][ ]可以看成当根为x时..有个背包空间为0~m...每个空间上记录了到到达这个空间的最大收益. ...
- poj 1155 TELE (树形背包dp)
本文出自 http://blog.csdn.net/shuangde800 题目链接: poj-1155 题意 某收费有线电视网计划转播一场重要的足球比赛.他们的转播网和用户终端构成一棵树状结构, ...
- poj 1155 TELE(树形DP)
TELE Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 4863 Accepted: 2673 Description ...
- poj 1155 树形背包
http://blog.csdn.net/libin56842/article/details/9908199 树形背包: 首先是建树,每个结构体为一个节点,包括下一个点序号,值,和next. tre ...
随机推荐
- 复习--二叉树&&树
树是一种很常用的数据结构,日后的学习中会经常碰到运用树的知识. //构造二叉树#include<cstdio> #include<iostream> #include<a ...
- Tool:ProcessOn
ylbtech-Tool:ProcessOn ProcessOn是一个面向垂直专业领域的作图工具和社交网络,成立于2011年6月并于2012年启动.ProcessOn将全球的专家顾问.咨询机构.BPM ...
- C/C++中输入多组数据方法
--------开始-------- 对于刚开始学编程的人来说每次基本上就是一次数据输入,多次的话基本也是会给定一个数组的大小,但随着做刷算法题开始,题目有的会不直接告诉输入几组数据,基本输入都是多组 ...
- CAS配置记录
CAS配置(1)之证书配置 CAS配置(2)之主配置 CAS配置(3)之restful-api接入接口
- Blender插件加载研究
目标 [x] 解析Blender插件代码加载原理, 为测试做准备 结论 采用方法3的方式, 可以在测试中保证重新加载子模块, 是想要的方式, 代码如下: _qk_locals = locals() d ...
- 通过Web Service实现IP地址查询功能
实例01 实现一个简单的Web服务访问 本实例将实现IP地址查询接口服务,根据用户传入的IP地址返回IP所在的省.市.地区,实例中将会用到IP地址库用于查询信息,由于数据较多,所以读者可在光盘资源文件 ...
- 1C课程笔记分享_StudyJams_2017
课程1C 概述 课程1C是创建一个生日贺卡应用的实践课程,所以本篇笔记分享主要记录个人的实践过程,此外分享一些比较零散的知识点. Drawable文件夹 Drawable文件夹是Android项目统一 ...
- Unity引擎GUI之Image
UGUI的Image等价于NGUI的Sprite组件,用于显示图片. 一.Image组件: Source Image(图像源):纹理格式为Sprite(2D and UI)的图片资源(导入图片后选择T ...
- Android ViewPager使用方法小结
android-support-v4.jar 是谷歌提供给我们的一个兼容低版本安卓设备的软件包,里面包囊了只有在 Android 3.0 以上可用的API.而 ViewPager 就是其中之一.利用它 ...
- C# 彻底关闭程序,包括循环
System.Environment.Exit(System.Environment.ExitCode); this.Dispose(); this.Close();