「ceoi 2009」harbingers
朴素 dp 大约就是 \(f_x=f_y+v_x\times(d_x-d_y)+s_x\),\(y\) 是 \(x\) 的祖先。这个式子可以斜率优化,在以 \(d_y\) 为横坐标,\(f_y\) 为纵坐标的坐标系中,斜率为 \(v_x\)。
我们应该用单调栈维护一个到根的树链。由于回溯的时候 \(v_x\) 不一定单调,取 \(f_x\) 的 dp 值时我们应该在完整的凸壳上二分。
插入决策点时,按照普通序列上的斜率优化弹栈(朴素)。很多人的问题是回溯还原栈状态的复杂度,其实你真正修改的值只有插入进去的位置,如果你没有使用 STL 的话弹栈的操作实际上是没有进行的,他们保留在栈中,只需要将栈顶指针还原即可,每次回溯的个数是 \(O(1)\) 级别的。
实际插入决策点时,因为时间复杂度的问题需要二分插入位置。如果你以乘代除,注意开 __int128
。
#include<bits/stdc++.h>
#define cmin(x, y) x = std::min(x, y)
#define cmax(x, y) x = std::max(x, y)
#define fors(i, l, r, ...) for(int i = (l), REP##i = (r), ##__VA_ARGS__; i <= REP##i; ++i)
#define dfors(i, r, l, ...) for(int i = (r), REP##i = (l), ##__VA_ARGS__; i >= REP##i; --i)
typedef long long ll;
int n, q[100100], l = 1, r;
ll f[100100], v[100100], s[100100], d[100100];
std::vector<std::pair<int, ll>> e[100100];
void pre_dfs(const int x, int fa) {
for(const auto [y, w] : e[x]) if(y != fa) d[y] = d[x]+w,pre_dfs(y, x);
}
ll up(const int i, const int j) { return f[j]-f[i]; }
ll down(const int i, const int j) { return d[j]-d[i]; }
ll cal(const int i, const int j) { return f[j]+v[i]*(d[i]-d[j])+s[i]; }
int bisect_optimal_decision(const ll k) {
int l = ::l, r = ::r, res = l; l++;
for(int mid; l <= r;) {
mid = (l+r)>>1;
if(up(q[mid-1], q[mid]) <= (__int128)k*down(q[mid-1], q[mid])) l = mid+1,res = mid;
else r = mid-1;
}
return q[res];
}
int bisect_insert_position(const int x) {
int l = ::l, r = ::r, res = l; l++;
for(int mid; l <= r;) {
mid = (l+r)>>1;
if((__int128)up(q[mid-1], q[mid])*down(q[mid], x) <= (__int128)up(q[mid], x)*down(q[mid-1], q[mid])) l = mid+1,res = mid;
else r = mid-1;
}
return res;
}
void dp_dfs(const int x, const int fa) {
if(x != 1) f[x] = cal(x, bisect_optimal_decision(v[x]));
int _r = r, t, tt;
r = bisect_insert_position(x);
t = r+1,tt = q[r+1],q[++r] = x;
for(const auto [y, w] : e[x]) if(y != fa) dp_dfs(y, x);
q[t] = tt,r = _r;
}
signed main() {
std::ios_base::sync_with_stdio(0);
std::cin.tie(0);
std::cin >> n;
fors(i, 1, n-1, x, y, z) {
std::cin >> x >> y >> z;
e[x].emplace_back(y, z);
e[y].emplace_back(x, z);
}
fors(i, 2, n) std::cin >> s[i] >> v[i];
pre_dfs(1, 0),dp_dfs(1, 0);
fors(i, 2, n) std::cout << f[i] << " \n"[i == n];
return 0;
}
「ceoi 2009」harbingers的更多相关文章
- 「BZOJ 1297」「SCOI 2009」迷路「矩阵乘法」
题意 边权\(w \in [1, 9]\)的\(n\)个结点的有向图,图上从\(1\)到\(n\)长度为\(d\)的路径计数,\(n \leq 10\). 题解 如果边权为\(1\)很经典,设\(f[ ...
- 「SDOI 2009」Elaxia的路线
发现自己这几天智商完全不在线-- 这道题的数据十分的水,怎样都可以艹过去-- 开始想了一个完全错误的算法,枚举一对点,判断这一对点是否同时在两条最短路上,是就用两点之间的路径更新答案.显然这样是错的: ...
- 「BZOJ 1876」「SDOI 2009」SuperGCD「数论」
题意 求\(\gcd(a, b)\),其中\(a,b\leq10^{10000}\) 题解 使用\(\text{Stein}\)算法,其原理是不断筛除因子\(2\)然后使用更相减损法 如果不筛\(2\ ...
- Solution -「CEOI 2017」「洛谷 P4654」Mousetrap
\(\mathscr{Description}\) Link. 在一个含 \(n\) 个结点的树形迷宫中,迷宫管理者菈米莉丝和一只老鼠博弈.老鼠初始时在结点 \(y\),有且仅有结点 \(x\ ...
- Solution -「CEOI 2006」「洛谷 P5974」ANTENNA
\(\mathcal{Description}\) Link. 给定平面上 \(n\) 个点,求最小的能覆盖其中至少 \(m\) 个点的圆半径及一个可能的圆心. \(n\le500\),坐 ...
- Solution -「HNOI 2009」「洛谷 P4727」图的同构计数
\(\mathcal{Description}\) Link. 求含 \(n\) 个点的无标号简单无向图的个数,答案模 \(997\). \(\mathcal{Solution}\) 首先 ...
- NLP领域的ImageNet时代到来:词嵌入「已死」,语言模型当立
http://3g.163.com/all/article/DM995J240511AQHO.html 选自the Gradient 作者:Sebastian Ruder 机器之心编译 计算机视觉领域 ...
- 前端构建工具之gulp(一)「图片压缩」
前端构建工具之gulp(一)「图片压缩」 已经很久没有写过博客了,现下终于事情少了,开始写博吧 今天网站要做一些优化:图片压缩,资源合并等 以前一直使用百度的FIS工具,但是FIS还没有提供图片压缩的 ...
- fir.im Weekly - 如何打造 Github 「爆款」开源项目
最近 Android 转用 Swift 的传闻甚嚣尘上,Swift 的 Github 主页上已经有了一次 merge>>「Port to Android」,让我们对 Swift 的想象又多 ...
- 更新日志 - fir.im「高级统计」功能上线
距离 2016 年到来只剩 10 个日夜,fir.im 也准备了一些新鲜的东西,比如「高级统计」功能和「跳转应用商店」功能,帮助你更好地管理.优化应用,欢迎大家试用反馈:) 新增高级统计功能 这次更新 ...
随机推荐
- 计算机视觉重磅会议VAlSE2023召开,合合信息分享智能文档处理技术前沿进展
近期,2023年度视觉与学习青年学者研讨会 (Vision And Learning SEminar, VALSE) 圆满落幕.会议由中国人工智能学会.中国图象图形学学会主办,江南大学和无锡国家高新技 ...
- gitlab docker升级报错
背景 使用docker部署gitlab(9.5.4)后,发现合并代码有问题 日志: 看gitlab官网此问题已修复,由于上传了一批代码,又懒得重建,决定对gitlab升级 docker启动命令: do ...
- 1.redis常见数据类型-字符串String、列表List、集合Set、Hash哈希、Zset有序集合
背景: 这里说的数据类型是value的数据类型,key的类型都是字符串. 命令不区分大小写,而key的值是区分大小写的 help @+数据类型 会出现命令提示 比如 help@string,help@ ...
- 如何将视频文件.h264和音频文件.mp3复用为输出文件output.mp4?
一.初始化复用器 在这个部分我们可以分三步进行:(1)打开输入视频文件上下文句柄 (2)打开输入音频文件上下文句柄 (3)打开输出文件上下文句柄 1.打开输入视频文件上下文句柄 在这一步,我们主要用到 ...
- 如何制作 GitHub 个人主页
人们在网上首先发现你的地方是哪里?也许你的社交媒体是人们搜索你时首先发现的东西,亦也许是你为自己创建的投资组合网站.然而,如果你使用GitHub来分享你的代码并参与开源项目,那么你的GitHub个人主 ...
- Kurator v0.4.0版本更新4大内容,满足多云环境的复杂需求
摘要:在最新发布的 v0.4.0 版本中,Kurator 进一步丰富了分布式云原生场景下的应用统一管理能力,以便更好地满足多云环境的复杂需求. 本文分享自华为云社区<Kurator v0.4.0 ...
- 瞬间抠图!揭秘 ZEGO 绿幕抠图算法背后的技术
抠图是图像处理中最常见的操作之一,指的是将图像中需要的部分从画面中精确的提取出来. 抠图的主要功能是为了后期的合成做准备.在 Photoshop 中,抠图的方法有很多种,最常见的有通道抠图.蒙版抠图. ...
- sensor有点意思之RCCB传感器
1.RCCB sensor 无意中看到一种特殊规格的传感器,RCCB (Red-Clear-Clear-Blue)sensor,第一次听到这个名词,咱不知道就查一查,检索到RCCB sensor是一种 ...
- Redis核心技术与实践 01 | 基本架构:一个键值数据库包含什么?
原文地址:https://time.geekbang.org/column/article/268262 个人博客地址:http://njpkhuan.cn/archives/redis-he-xin ...
- .NET程序的 GDI句柄泄露 的再反思
一:背景 1. 讲故事 上个月我写过一篇 如何洞察 C# 程序的 GDI 句柄泄露 文章,当时用的是 GDIView + WinDbg 把问题搞定,前者用来定位泄露资源,后者用来定位泄露代码,后面有朋 ...