Problem

辣鸡bzoj权限题,洛谷链接

题意概要:一棵 \(n\) 个点有根树。\(Q\) 次询问给出一个 \(K\),回答遍历完整棵树所需最少操作次数。每次操作可以选择访问不超过 \(K\) 个未访问的点,且这些点的父亲必须在之前被访问过。

Solution

一开始题意理解错了,以为同时段每个点都能扩展 \(k\) 次,然后就无耻地看了题解……但是有个证明网上都没写,这也正是写这篇博客的原因

大概意思是说,最优策略一定是先用 \(i\) 步取完前 \(i\) 层,然后选取剩下深度大于 \(i\) 的节点时每次都能取满。规范一下就是设 \(s[i]\) 表示深度大于 \(i\) 的节点个数,则答案为 \(\max\limits_{i=1}^n \{i+\lceil \frac {s[i]}k\rceil\}\)

然后就可以正常斜率优化了:维护点 \((i,s[i])\) 的上凸包,每次询问 \(i\) 则在凸包上找斜率为 \(-i\) 的直线所切的点

但是看题解的时候不清楚前边那个式子的正确性,为什么会存在一条分界线使得上面可以用 \(i\) 次选完 \(i\) 层,下面可以随意选

思考了一会才弄懂,对于一棵树,从底层选择一个最深的深度 \(d\),显然满足下部节点可以随意选择(目前没有下部节点),但是有可能上部节点不能在层数次内选完。若出现这种情况,则上部一定存在若干层节点特别多,导致无法消完,可以考虑将分界线挪到某一层的上一层,由于这层节点特别多,可以保证下部节点可以随意选择。所以存在分界线比深度 \(d\) 浅,将 \(d\) 减小继续判断直到无法挪动,则找到分界线

至于为什么 \(\max\limits_{i=1}^n \{i+\lceil \frac {s[i]}k\rceil\}\) 中取最大值即可,是因为如若没有选择到分界线,则算出的值一定比最终答案要小

Code

#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
typedef double db; template <typename _tp> inline void read(_tp&x){
char c11=getchar();x=0;while(!isdigit(c11))c11=getchar();
while(isdigit(c11))x=x*10+c11-'0',c11=getchar();
} const int N = 1001000;
struct Edge{int v,nxt;} a[N+N];
int head[N], s[N], Ans[N], qy[N];
ll f[N];
int n,Q,tp,_,mxd; void dfs(int x,int ds){
++s[ds], mxd = max(mxd, ds);
for(int i=head[x];i;i=a[i].nxt)
dfs(a[i].v,ds+1);
} struct vec{
ll x,y;
inline void in(){read(x), read(y);}
friend inline vec operator - (const vec&A,const vec&B) {return (vec){A.x - B.x, A.y - B.y};}
friend inline db operator * (const vec&A,const vec&B) {return (db)A.x * B.y - (db)A.y * B.x;}
friend inline bool operator < (const vec&A,const vec&B) {return A.x!=B.x ? A.x<B.x : A.y>B.y;}
}p[N],stk[N]; int main(){
read(n), read(Q);
for(int i=1;i<=Q;++i) read(qy[i]);
for(int i=2,x;i<=n;++i) read(x), a[++_].v = i, a[_].nxt = head[x], head[x] = _;
dfs(1,0);
for(int i=n;~i;--i) s[i] += s[i+1];
for(int i=0;;++i){
vec nw = (vec) {i, s[i]};
while(tp > 1 and (stk[tp] - stk[tp-1]) * (nw - stk[tp]) >= 0) --tp;
stk[++tp] = nw;
if(!s[i]) break;
}
for(int i=1,t=1;i<=n;++i){
vec dir = (vec) {1, -i};
while(t < tp and (stk[t+1] - stk[t]) * dir < 0) ++t;
Ans[i] = (stk[t].y + (ll)i * stk[t].x + i-1) / i;
}
++mxd;
for(int i=1;i<=Q;++i){
if(Ans[qy[i]]) printf("%d ",Ans[qy[i]]);
else printf("%d ",mxd);
}
return 0;
}

题解-POI2014 Supercomputer的更多相关文章

  1. 【BZOJ】3835: [Poi2014]Supercomputer

    题意 \(n(1 \le 1000000)\)个点的有根树,\(1\)号点为根,\(q(1 \le 1000000)\)次询问,每次给一个\(k\),每一次可以选择\(k\)个未访问的点,且父亲是访问 ...

  2. BZOJ3835: [Poi2014]Supercomputer

    Description Byteasar has designed a supercomputer of novel architecture. It may comprise of many (id ...

  3. BZOJ3835[Poi2014]Supercomputer——斜率优化

    题目描述 Byteasar has designed a supercomputer of novel architecture. It may comprise of many (identical ...

  4. BZOJ3835 [Poi2014]Supercomputer 【斜率优化】

    题目链接 BZOJ3835 题解 对于\(k\),设\(s[i]\)为深度大于\(i\)的点数 \[ans = max\{i + \lceil \frac{s[i]}{k}\} \rceil\] 最优 ...

  5. 题解-POI2014 FAR-FarmCraft

    Problem bzoj权限题,洛谷上可提交 洛谷上的奇葩翻译不要看,很多条件缺漏 题意简述:给定一棵树,每条边权为1,给定所有点点权,每条边仅能走两次,求以一定顺序遍历整棵树后,使所有点中的到达时间 ...

  6. [POI2014]Supercomputer

    题目大意: 给定一个$n(n\le10^6)$个结点的有根树,从根结点开始染色.每次可以染和已染色结点相邻的任意$k$个结点.$q(q\le10^6)$组询问,每次给定$k$,问至少需要染几次? 思路 ...

  7. POI2014题解

    POI2014题解 [BZOJ3521][Poi2014]Salad Bar 把p当作\(1\),把j当作\(-1\),然后做一遍前缀和. 一个合法区间\([l,r]\)要满足条件就需要满足所有前缀和 ...

  8. bzoj AC倒序

    Search GO 说明:输入题号直接进入相应题目,如需搜索含数字的题目,请在关键词前加单引号 Problem ID Title Source AC Submit Y 1000 A+B Problem ...

  9. BZOJ3524 & LOJ2432:[POI2014]代理商Couriers——题解

    https://www.lydsy.com/JudgeOnline/problem.php?id=3524 https://loj.ac/problem/2432 给一个长度为n的序列a.1≤a[i] ...

随机推荐

  1. Javascript实现base64的加密解密

    //1.加密解密方法使用: //1.加密 var str = '124中文内容'; var base = new Base64(); var result = base.encode(str); // ...

  2. array数组(n,1)和(n,)互相转换

    data.shape #(172,1) result = [arr[0] for arr in data] result.shape #(172,) (172,1)表示是一个(172,1)shape大 ...

  3. python正则匹配示例

    text="山东省临沂市兰山区 市委大院中区21号楼4单元 276002 奥特曼1号 18254998111" #匹配手机号 m=re.findall(r"1\d{10} ...

  4. Adding appsettings.json to a .NET Core console app

    This is something that strangely doesn’t seem to be that well documented and took me a while to figu ...

  5. 调试ucosii_pendsv中断函数有感

    发现自己的代码的意思和自己理解的意思有不相同的时候,自己先用printf打印输出分析 当发现是自己那一个知识点没有掌握好时,自己用其他的C编译器,仿写用到的知识点的程序,然后掌握该知识点. 最后实在找 ...

  6. Spring MVC 使用介绍(十三)数据验证 (一)基本介绍

    一.消息处理功能 Spring提供MessageSource接口用于提供消息处理功能: public interface MessageSource { String getMessage(Strin ...

  7. 【BZOJ4030】[HEOI2015]小L的白日梦

    [BZOJ4030][HEOI2015]小L的白日梦 题面 BZOJ 洛谷 题解 要求的是最小的不开心连续段的期望. 然后发现自己就不会做了. 然后就可以来抄题解啦. 首先来猜性质: 第一个,一定是按 ...

  8. 20165223《网络对抗技术》Exp2 后门原理与实践

    目录 -- 后门原理与实践 后门原理与实践说明 实验任务 基础知识问答 常用后门工具 实验内容 任务一:使用netcat获取主机操作Shell,cron启动 任务二:使用socat获取主机操作Shel ...

  9. [HNOI2007]神奇游乐园(插头DP)

    题意:n*m的矩阵内值有正有负,找一个四连通的简单环(长度>=4),使得环上值的和最大. 题解:看到2<=m<=6和简单环,很容易想到插头DP,设f[i][j][k]表示轮廓线为第i ...

  10. css解决内联元素间的空白间隔

    在内联元素的父级元素上设置font-size: 0px;即可.例如: <div class="wrap"> <ul> <li class=" ...