http://cogs.pro:8080/cogs/problem/problem.php?pid=vSXNiVegV

题意:给个树,第i个点有两个权值ai和bi,现在求一条长度为m的路径,使得Σai/Σbi最小。

思路:二分答案得p,把每个点权值变成ai-p*bi,看是否存在长为一条长为m的路使总和<=0。

tag数组表示从当前位置沿最长链走到底的值,dp数组初值表示从当前位置的重儿子走到底的值(加负号),用tag[...]+dp[..]维护从当前节点往下走若干步得到的最小值(只更新dp数组

 # include <stdio.h>
# include <string.h>
# include <iostream>
# include <algorithm>
// # include <bits/stdc++.h> using namespace std; typedef long long ll;
typedef long double ld;
typedef unsigned long long ull;
const int N = 3e4 + , M = 6e4 + ;
const int mod = 1e9+; int n, m, A[N * ], B[N * ], head[N], nxt[M], to[M], tot = ;
inline void add(int u, int v) {
++tot; nxt[tot] = head[u]; head[u] = tot; to[tot] = v;
}
inline void adde(int u, int v) {
add(u, v), add(v, u);
} int dep[N], mxd[N], son[N], sz[N];
inline void pre_dfs(int x, int fa = ) {
dep[x] = dep[fa] + ;
mxd[x] = dep[x]; son[x] = ;
for (int i=head[x]; i; i=nxt[i]) {
if(to[i] == fa) continue;
pre_dfs(to[i], x);
if(mxd[to[i]] > mxd[x]) mxd[x] = mxd[to[i]], son[x] = to[i];
}
sz[x] = mxd[x] - dep[x];
} int pos[N], idx;
inline void pre_pos(int x, int fa = ) {
pos[x] = ++idx;
if(son[x]) pre_pos(son[x], x);
for (int i=head[x]; i; i=nxt[i])
if(to[i] != fa && to[i] != son[x]) pre_pos(to[i], x);
} double mid_check, ans;
double dp[N], tag[N];
inline void solve(int x, int fa = ) {
double *f = &dp[pos[x]], C = (double)A[x] - mid_check * B[x];
if(son[x] == ) { //leaf
f[] = ; tag[x] = C;
if(m == ) ans = min(ans, tag[x]);
return ;
}
solve(son[x], x); f[] = -tag[son[x]];
tag[x] = tag[son[x]] + C;
for (int i=head[x], y; i; i=nxt[i]) {
if(to[i] == fa || to[i] == son[x]) continue;
solve(y = to[i], x);
double *g = &dp[pos[y]];
for (int j=; j<=sz[y] && j<m; ++j)
if(m--j <= sz[x]) ans = min(ans, f[m--j] + tag[x] + g[j] + tag[y]);
for (int j=; j<=sz[y]; ++j) f[j+] = min(f[j+], g[j] + tag[y] + C - tag[x]);
}
if(m <= sz[x]) ans = min(ans, f[m] + tag[x]);
} inline bool chk(double x) {
ans = 1e18; mid_check = x;
solve();
return ans <= ;
} int main() {
freopen("cdcq_b.in", "r", stdin);
freopen("cdcq_b.out", "w", stdout);
cin >> n >> m;
for (int i=; i<=n; ++i) scanf("%d", A+i);
for (int i=; i<=n; ++i) scanf("%d", B+i);
if(m == -) {
double ans = 1e18;
for (int i=; i<=n; ++i) ans = min(ans, (double)A[i]/B[i]);
printf("%.2lf\n", ans);
return ;
}
for (int i=, u, v; i<n; ++i) {
scanf("%d%d", &u, &v);
adde(u, v);
}
--m;
pre_dfs();
pre_pos();
double l = , r = 1e11, mid;
while(r-l > 1e-) {
mid = (l+r)/2.0;
if(chk(mid)) r = mid;
else l = mid;
}
if(l > 5e10) puts("-1");
else printf("%.2lf\n", l);
return ;
}

cogs 2652. 秘术「天文密葬法」(0/1分数规划 长链剖分 二分答案 dp的更多相关文章

  1. 【COGS2652】秘术「天文密葬法」(长链剖分,分数规划)

    [COGS2652]秘术「天文密葬法」(长链剖分,分数规划) 题面 Cogs 上面废话真多,建议直接拉到最下面看一句话题意吧: 给个树,第i个点有两个权值ai和bi,现在求一条长度为m的路径,使得Σa ...

  2. [COGS2652]秘术「天文密葬法」

    description 题面 给个树,第\(i\)个点有两个权值\(a_i\)和\(b_i\),现在求一条长度为\(m\)的路径,使得\(\frac{\sum a_i}{\sum b_i}\)最小 d ...

  3. 【LOJ】#3014. 「JOI 2019 Final」独特的城市(长链剖分)

    LOJ#3014. 「JOI 2019 Final」独特的城市(长链剖分) 显然我们画一条直径,容易发现被统计的只可能是直径某个距离较远的端点到这个点的路径上的值 用一个栈统计可以被统计的点,然后我们 ...

  4. 2019.03.11 COGS2652 秘术(天文密葬法)(分数规划+长链剖分)

    传送门 题意:nnn个点的树,每个点两个值a,ba,ba,b,问长度为mmm的路径∑ai∑bi\frac{\sum a_i}{\sum b_i}∑bi​∑ai​​的最大值. 思路:一眼要01分数规划, ...

  5. 「vijos」lxhgww的奇思妙想(长链剖分)

    传送门 长链剖分的板子(又是乱搞优化暴力) 对于每一个点,我们定义它深度最深的子节点为它的重儿子(为什么不叫长儿子……),他们之间的连边为重边 然后长链剖分有几个性质 1.总链长为$O(n)$ 2.一 ...

  6. P7581-「RdOI R2」路径权值【长链剖分,dp】

    正题 题目链接:https://www.luogu.com.cn/problem/P7581 题目大意 给出\(n\)个点的有边权有根树,\(m\)次询问一个节点\(x\)的所有\(k\)级儿子两两之 ...

  7. 「WC2010」重建计划(长链剖分/点分治)

    「WC2010」重建计划(长链剖分/点分治) 题目描述 有一棵大小为 \(n\) 的树,给定 \(L, R\) ,要求找到一条长度在 \([L, R]\) 的路径,并且路径上边权的平均值最大 \(1 ...

  8. LOJ 3089 「BJOI2019」奥术神杖——AC自动机DP+0/1分数规划

    题目:https://loj.ac/problem/3089 没想到把根号之类的求对数变成算数平均值.写了个只能得15分的暴力. #include<cstdio> #include< ...

  9. 「NOI2015」「Codevs4621」软件包管理器(树链剖分

    4621 [NOI2015]软件包管理器 时间限制: 1 s 空间限制: 256000 KB 题目等级 : 钻石 Diamond   题目描述 Description Linux用户和OSX用户一定对 ...

随机推荐

  1. 常用GDB命令行调试命令

    po po是print-object的简写,可用来打印所有NSObject对象.使用举例如下: (gdb) po self <LauncherViewController: 0x552c570& ...

  2. 提交bug的标准及书写规范

    Bug有效性 1.交付过程中测试者需按照专家设定好的模块,对Bug进行归类提交: 2.Bug的类型默认为UI问题.功能问题.崩溃问题,提交Bug时不能弄错: 3.需求是否明确.前提条件是否满足.输入数 ...

  3. Selenium+java - 借助autolt完成上传文件操作

    写在前面: 上传文件是每个自动化测试同学会遇到,而且可以说是面试必考的问题,标准控件我们一般用sendkeys()就能完成上传,但是我们的测试网站的上传控件一般为自己封装的,用传统的上传已经不好用了, ...

  4. 神奇的 SQL 之子查询,细节满满 !

    前言 开心一刻 有一天,麻雀遇见一只乌鸦. 麻雀问:你是啥子鸟哟 ? 乌鸦说:我是凤凰. 麻雀说:哪有你龟儿子这么黢黑的凤凰 ? 乌鸦说:你懂个铲铲,老子是烧锅炉的凤凰. 子查询 讲子查询之前,我们先 ...

  5. 1关于如何用Navicat连接到xampp安装的mysql

    打开xampp,打开config打开my.ini. 检索bind-address,后面的数字是你的IP地址 检索 port,后面的数字是端口号 打开Navicat新建连接,选中mysql 连接名随便起 ...

  6. 【PYTHON】语法基础 | 开始使用Python

    Python的热度不言而喻,机器学习.数据分析的首选语言都是Python,想要学习Python的小伙伴也很多,我之前也没有认真用过Python,所以也想体验一下它的魅力,索性花了两天集中看了一下它的基 ...

  7. word2vec原理分析

    本文摘录整编了一些理论介绍,推导了word2vec中的数学原理,理论部分大量参考<word2vec中的数学原理详解>. 背景 语言模型 在统计自然语言处理中,语言模型指的是计算一个句子的概 ...

  8. spark源码阅读---Utils.getCallSite

    1 作用 当该方法在spark内部代码中调用时,会返回当前调用spark代码的用户类的名称,以及其所调用的spark方法.所谓用户类,就是我们这些用户使用spark api的类. 2 内部实现 2.1 ...

  9. 帝国CMS(EmpireCMS) v7.5 代码注入分析(CVE-2018-19462)

    帝国CMS(EmpireCMS) v7.5 代码注入分析(CVE-2018-19462) 一.漏洞描述 EmpireCMS7.5及之前版本中的admindbDoSql.php文件存在代码注入漏洞.该漏 ...

  10. tensorflow学习笔记——多线程输入数据处理框架

    之前我们学习使用TensorFlow对图像数据进行预处理的方法.虽然使用这些图像数据预处理的方法可以减少无关因素对图像识别模型效果的影响,但这些复杂的预处理过程也会减慢整个训练过程.为了避免图像预处理 ...