正解:树型dp

解题报告:

传送门!

简要题意:有棵树,每个节点有个权值w,要求选k个节点,最大化∑dis*w,其中如果某个节点到根的路径上选了别的节点,dis指的是到达那个节点的距离

首先这个一看就是个树型dp嘛,关键是怎么设状态

首先肯定是想到设f[i][j]:以i为根的子树中选了j个点

这个时候发现布星昂,这么设的时候我们不能得到对于到根的路径上的点的贡献鸭,所以就考虑加一维

所以f[i][j][k]:以i为根的子树中选了j个点,最近祖先的距离为k的最大代价

然后直接转移就好

对了还要说一个就,我这里有转点儿题意?就它是问最小化花费,然后我写题解的时候是转化成的tot-max∑

但实际实现的时候我是直着写的就是说直接最小化花费打的QAQ

差不多差不多QAQ

然后我发现我现在码力是真的弱,,,,我知道这题正解了,还是个dp题,然后打了2h?我原地自杀了要,,,

#include<bits/stdc++.h>
using namespace std;
#define il inline
#define fr first
#define sc second
#define rg register
#define gc getchar()
#define ll long long
#define mp make_pair
#define rp(i,x,y) for(rg int i=x;i<=y;++i)
#define my(i,x,y) for(rg int i=x;i>=y;--i)
const int N=100+2,K=50+2;
int n,k,w[N],stck_top,stck[N],dis[N];
ll f[N][K][N][2];
vector< pair<int,int> >son[N];
il int read()
{
rg char ch=gc;rg int x=0;rg bool y=1;
while(ch!='-' && (ch>'9' || ch<'0'))ch=gc;
if(ch=='-')ch=gc,y=0;
while(ch>='0' && ch<='9')x=(x<<1)+(x<<3)+(ch^'0'),ch=gc;
return y?x:-x;
}
il void dfs(int nw)
{
stck[++stck_top]=nw;
int sz=son[nw].size();
rp(i,0,sz-1)
{
dis[son[nw][i].fr]=dis[nw]+son[nw][i].sc;dfs(son[nw][i].fr);
my(j,stck_top,1)
{
my(p,k,0)
{
f[nw][p][stck[j]][0]+=f[son[nw][i].fr][0][stck[j]][0];
f[nw][p][stck[j]][1]+=f[son[nw][i].fr][0][nw][0];
my(q,p,0)
{
f[nw][p][stck[j]][0]=min(f[nw][p][stck[j]][0],f[son[nw][i].fr][q][stck[j]][0]+f[nw][p-q][stck[j]][0]),
f[nw][p][stck[j]][1]=min(f[nw][p][stck[j]][1],f[son[nw][i].fr][q][nw][0]+f[nw][p-q][stck[j]][1]);
}
}
}
}
rp(i,1,stck_top)
{
my(j,k,0)
if(j)f[nw][j][stck[i]][0]=min(f[nw][j-1][stck[i]][1],f[nw][j][stck[i]][0]+w[nw]*(dis[nw]-dis[stck[i]]));
else f[nw][j][stck[i]][0]+=w[nw]*(dis[nw]-dis[stck[i]]);
}
--stck_top;
return;
}
int main()
{
//     freopen("riv.in","r",stdin);freopen("riv.out","w",stdout);
n=read();k=read();
rp(i,1,n){w[i]=read();int fa=read(),dis=read();son[fa].push_back(mp(i,dis));}
dfs(0);printf("%lld\n",f[0][k][0][0]);
return 0;
}

最后放下代码QAQ

顺便港下,这题有个双倍经验

都差不多只是还要建棵trie树就好了,over

等下把那题代码也放上来吼QwQ

#include<bits/stdc++.h>
using namespace std;
#define il inline
#define fr first
#define sc second
#define rg register
#define gc getchar()
#define ll long long
#define mp make_pair
#define rp(i,x,y) for(rg int i=x;i<=y;++i)
#define my(i,x,y) for(rg int i=x;i>=y;--i)
const int N=500+2,K=10+2;
int n,k,stck_top,stck[N],dis[N],nod_cnt;
ll f[N][K][N][2],as;
struct node{int to[10],wei;}tr[N*100];
il int read()
{
rg char ch=gc;rg int x=0;rg bool y=1;
while(ch!='-' && (ch>'9' || ch<'0'))ch=gc;
if(ch=='-')ch=gc,y=0;
while(ch>='0' && ch<='9')x=(x<<1)+(x<<3)+(ch^'0'),ch=gc;
return y?x:-x;
}
il void insert(string str,ll wei)
{
ll lth=str.length(),nw=0;
rp(i,0,lth-1)
{
if(!tr[nw].to[str[i]^'0'])tr[nw].to[str[i]^'0']=++nod_cnt;
nw=tr[nw].to[str[i]^'0'];tr[nw].wei+=wei;
}
}
il void dfs(int nw)
{
stck[++stck_top]=nw;
rp(i,0,9)
{
if(!tr[nw].to[i])continue;dis[tr[nw].to[i]]=dis[nw]+1;dfs(tr[nw].to[i]);
my(j,stck_top,1)
my(p,k,0)
my(q,p,0)
f[nw][p][stck[j]][0]=max(f[nw][p][stck[j]][0],f[tr[nw].to[i]][q][stck[j]][0]+f[nw][p-q][stck[j]][0]),
f[nw][p][stck[j]][1]=max(f[nw][p][stck[j]][1],f[tr[nw].to[i]][q][nw][0]+f[nw][p-q][stck[j]][1]);
}
rp(i,1,stck_top)
my(j,k,0)
if(j)f[nw][j][stck[i]][0]=max(f[nw][j-1][stck[i]][1]+tr[nw].wei*(dis[nw]-dis[stck[i]]),f[nw][j][stck[i]][0]);
--stck_top;
return;
}
int main()
{
//     freopen("sd.in","r",stdin);freopen("sd.out","w",stdout);
n=read();k=read();rp(i,1,n){string str;cin>>str;ll wei=read();insert(str,wei);as+=str.length()*wei;}
dfs(0);printf("%lld\n",as-f[0][k][0][0]);
return 0;
}

因为一些,奇怪的问题,我发现我顺着做布星,按上面那个as-=max的思路就欧克,,,

洛谷P3354 Riv河流 [IOI2005] 树型dp相关推荐

  1. 洛谷 P3384 【模板】树链剖分-树链剖分(点权)(路径节点更新、路径求和、子树节点更新、子树求和)模板-备注结合一下以前写的题目,懒得写很详细的注释...

    P3384 [模板]树链剖分 题目描述 如题,已知一棵包含N个结点的树(连通且无环),每个节点上包含一个数值,需要支持以下操作: 操作1: 格式: 1 x y z 表示将树从x到y结点最短路径上所有节 ...

  2. 洛谷P4315 月下“毛景树” 题解

    洛谷P4315 月下"毛景树" 题解 题目链接:P4315 月下"毛景树" 题意:请维护一个数据结构,支持 改第 kkk 条边的边权 结点 uuu 到 vvv ...

  3. 洛谷——P1047 校门外的树 python实现

    洛谷--P1047 校门外的树 python实现 l, m = map(int, input().split(' ')) trees = [True]*(l+1) for i in range(m): ...

  4. 其他OJ 树型DP 选课

    在朱全民的PPT介绍的一个树型DP经典题,<选课>,中文题目,不结束 找了很久找到了可以提交的OJ,重庆八中 http://www.cqoi.net:2012/JudgeOnline/pr ...

  5. 【树型DP】BZOJ1564 二叉查找树(noi2009)

    标签: 二叉查找树 [题目描述] 已知一棵特殊的二叉查找树.根据定义,该二叉查找树中每个结点的数据值都比它左儿子结点的数据值大,而比它右儿子结点的数据值小. 另一方面,这棵查找树中每个结点都有一个权值 ...

  6. 【树型DP】加分二叉树

    问题 b: [树型DP]加分二叉树 时间限制: 1 Sec  内存限制: 64 MB 提交: 8  解决: 6 [提交] [状态] [讨论版] [命题人:admin] 题目描述 科技忽略了过程就是魔法 ...

  7. 二叉苹果树(树型DP+背包)

    二叉苹果树 有一棵苹果树,如果树枝有分叉,一定是分2叉(就是说没有只有1个儿子的结点).这棵树共有N个结点(叶子点或者树枝分叉点),编号为1-N,树根编号一定是1. 我们用一根树枝两端连接的结点的编号 ...

  8. POJ3342 Party at Hali-Bula(树型DP求最大独立集+唯一解判断)

    题意: 公司参加聚会,要求员工不能和他的上司同时参加,求最多能参加几个人并且判断解是否唯一. 要点: 树型DP的经典题,用dp[u][1]表示选取u的最大值,dp[u][0]表示不选取u的最大值,容易 ...

  9. 虚树+树型DP SDOI2011消耗战

    <虚树+树型DP> SDOI2011消耗战 #include <iostream> #include <cstdio> #include <cstring&g ...

最新文章

  1. OneZero第五周第二次站立会议(2016.4.19)
  2. 全球及中国水产加工市场消费潜力分析与投资规模建议报告2022版
  3. 以太坊源码学习 -- EVM
  4. 怎样快速掌握深度学习TensorFlow框架?
  5. 小菜:关于main方法的面试题
  6. ORACLE 进入sqlplus的协议适配器错误
  7. python数据库增删改查_python对数据库mysql的操作(增删改查)
  8. Javascript事件模型系列(一)事件及事件的三种模型
  9. 4t硬盘实际容量是多少_4TB超大容量+便携实用的移动硬盘-东芝A3移动硬盘体验
  10. 超全AD软件3D封装库 免费分享!
  11. 计算机二级数据库题库百度云,计算机二级数据库试题及答案
  12. COPRA RF 2005 SR1冷弯成型,轧辊设计 USB加密锁
  13. 《Dreamweaver CS6 完全自学教程》笔记 第一章:网页制作基础知识
  14. spring boot与kafka
  15. 服务器虚拟化的分类宿主模型,虚拟化分类
  16. L - Evenly Separated Strings
  17. ROS三轮全向轮移动底盘 (01)
  18. ffmpeg m3u8 与 mp4 相互转换
  19. 特征选择方法详解Part2-卡方检验、互信息(Mutual Information)
  20. Vmware虚拟机文件介绍、克隆及文件名称更改方法

热门文章

  1. 微小宝公众号排行榜_公众号排名 | 2020年2月公众号地区排行榜重磅发布
  2. winform 三层(BLL.DAL.MODEL)
  3. 前端实现3D旋转木马相册
  4. 二进制安装k8s v1.22.8集群
  5. C/C++程序的编译过程
  6. 你看到的都是招数,不是内功
  7. 伊朗加油站遭网络攻击致瘫痪、Babuk勒索软件源代码泄露|10月28日全球网络安全热点
  8. 在 Java 项目中,如何使用 Error 日志更加方便排查问题,这才是正确姿势,非常实用!...
  9. Mysql 存储过程详解(procedure)
  10. 0522模拟赛 A. 求和 B.农民(farmer) C.仙人掌