【HDU 5956】The Elder(树上斜率DP)
思路:
树形DP,dp[i]=min(dp[j]+(sum[i]-sum[j])^2+p) (j是i的祖先即j<i) ,用斜率将复杂度由O(n^2)优化为O(n)。
附上一篇优秀的斜率DP的讲解
此外,在pop的时候可以二分,会更优一些。
但是感觉写起来有点麻烦,这个题不二分的话,时间也稳稳地不会T的。
代码:
#include<iostream>
#include<cstdio>
#include<cstring>
#include<queue>
#include<stack>
using namespace std;
const int N=1e5+100;
const int M=2e5+100;
long long sum[N];
long long dp[N];
long long ans;
long long p;
int head[N];
int cnt;
struct node
{int op;//1-pu_f 2-pu_b 3-po_f 4-po_bint x;node(){}node(int op,int x):op(op),x(x){}
}now;
deque<int> q;
stack<node> s;
struct edge
{int v;long long w;int next;
}e[M];
void init()
{cnt=0;ans=0;memset(head,-1,sizeof(head));while(!q.empty())q.pop_back();while(!s.empty())s.pop();
}
void add(int u,int v,long long w)
{e[cnt].v=v;e[cnt].w=w;e[cnt].next=head[u];head[u]=cnt++;
}
void dfs(int cur,int fa)
{if(cur!=1){dp[cur]=dp[q.front()]+(sum[cur]-sum[q.front()])*(sum[cur]-sum[q.front()])+p;while(q.size()>=2&&dp[q[1]]+(sum[cur]-sum[q[1]])*(sum[cur]-sum[q[1]])+p<dp[cur]){dp[cur]=dp[q[1]]+(sum[cur]-sum[q[1]])*(sum[cur]-sum[q[1]])+p;s.push(node(3,q.front()));q.pop_front();}ans=max(ans,dp[cur]);while(q.size()>=2&&(dp[cur]+sum[cur]*sum[cur]-(dp[q.back()]+sum[q.back()]*sum[q.back()]))*2*(sum[q.back()]-sum[q[q.size()-2]])<(dp[q.back()]+sum[q.back()]*sum[q.back()]-(dp[q[q.size()-2]]+sum[q[q.size()-2]]*sum[q[q.size()-2]]))*2*(sum[cur]-sum[q.back()])){s.push(node(4,q.back()));q.pop_back();}s.push(node(2,cur));q.push_back(cur);}int ss=s.size();for(int i=head[cur];i!=-1;i=e[i].next){if(e[i].v!=fa){sum[e[i].v]=sum[cur]+e[i].w;dfs(e[i].v,cur);while(s.size()>ss){now=s.top();s.pop();if(now.op==1)q.pop_front();else if(now.op==2)q.pop_back();else if(now.op==3)q.push_front(now.x);elseq.push_back(now.x);}}}
}
int main()
{int t;int n;int u,v;long long w;scanf("%d",&t);while(t--){scanf("%d%lld",&n,&p);init();for(int i=1;i<n;++i){scanf("%d%d%lld",&u,&v,&w);add(u,v,w);add(v,u,w);}dp[1]=-p;sum[1]=0;q.push_back(1);dfs(1,-1);printf("%lld\n",ans);}return 0;}
【HDU 5956】The Elder(树上斜率DP)相关推荐
- The Elder HDU - 5956
/* 树上斜率优化 一开始想的是构造出一个序列 转化成一般的dp但是可能被卡 扫把状的树的话可能变成n*n 其实可以直接在树上维护这个单调队列 dfs虽然搞得是一棵树,但是每次都是dfs到的都是一个序 ...
- HDU 3669 Cross the Wall(斜率DP+预处理)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3669 题目大意:有n(n<=50000)个矩形,每个矩形都有高和宽,你可以在墙上最多挖k个洞使得 ...
- HDU 3507 Print Article(斜率优化DP)
题目链接 题意 : 一篇文章有n个单词,如果每行打印k个单词,那这行的花费是,问你怎么安排能够得到最小花费,输出最小花费. 思路 : 一开始想的简单了以为是背包,后来才知道是斜率优化DP,然后看了网上 ...
- hdu 3480 斜率dp
思路:很普通的斜率dp #include<cstdio> #include<cstring> #include<iostream> #include<algo ...
- HDU 1520 Anniversary party(树形dp)
HDU 1520 Anniversary party(树形dp) 树形dp第一题!!! 题意很清晰,思路也很明确.很容易找到根节点,即最大的boss,通过根节点向下dp. 状态转移方程: int to ...
- HDU 3001 三进制状压DP
HDU 3001 三进制状压DP N个城市,M条道路,每条道路有其经过的代价,每一个城市最多能够到达两次,求走全然部城市最小代价,起点随意. 三进制状压.存储每一个状态下每一个城市经过的次数. 转移方 ...
- bzoj 3437: 小P的牧场(斜率DP)
3437: 小P的牧场 Time Limit: 10 Sec Memory Limit: 128 MB Submit: 1493 Solved: 830 [Submit][Status][Disc ...
- hdu 5155 Harry And Magic Box(DP)
题目链接:hdu 5155 Harry And Magic Box dp[i][j]表示i∗j的矩阵方案数,dp[i][j]从dp[i−k][j−1]中转移,枚举前面j-1列中k行为空,那么这些行在第 ...
- hdu 3401 Trade(单调队列优化dp)
hdu 3401 Trade(单调队列优化dp) 题意:lxhgww喜欢炒股票,他可以在第i天买入或者卖出若干张股票(一天只能买或者卖),两个交易日之间至少相隔w天,问他t天后最多能赚多少. 解题思路 ...
- hdu 2993 MAX Average Problem 斜率优化DP
详见,算法合集之<浅谈数形结合思想在信息学竞赛中的应用>. #include<cstdio> #include<cstring> #include<algor ...
最新文章
- 深入浅出Android动态载入jar包技术
- BZOJ2743 [HEOI2012]采花
- unilever news
- Linux网络基本网络配置
- spark 2.2 读取 Hadoop3.0 数据异常 org.apache.hadoop.hdfs.web.HftpFileSystem cannot access its superinterfa
- Django REST框架 -1
- 那个马斯克的小迷弟开始讲深度学习了,课程视频+PPT已放出
- SQL AZURE数据库创建,云计算体验之一
- Minitab 控制图
- pr下载与安装(含安装包百度网盘链接)
- Java第一天笔记01——jdk8的安装与环境变量的配置
- MISC之常用编码总结
- 人工智能基础:人工智能云服务(Alaas)介绍
- MPC5744P-UART(LIN)模块
- iphone相册照片路径_如何使用相册整理iPhone照片
- C语言模拟实现:atoi函数
- IDEA相对路径系统找不到指定的文件问题
- php从气象局获取天气预报并保存到服务器
- 蓝桥杯 — 超声波测距模块的使用
- java git打包iOS_懒人做iOS系列之jenkins+git+fir打包(xCode9)