bzoj2117
动态电分治+二分
肯定要枚举所有点对,那么我们建出点分树降低树高,然后每个点存下点分树中所有子树到这个点的距离,然后二分+lower_bound就行了。
#include<bits/stdc++.h>
using namespace std;
const int N = 2e5 + ;
namespace IO
{
const int Maxlen = N * ;
char buf[Maxlen], *C = buf;
int Len;
inline void read_in()
{
Len = fread(C, , Maxlen, stdin);
buf[Len] = '\0';
}
inline void fread(int &x)
{
x = ;
int f = ;
while (*C < '' || '' < *C) { if(*C == '-') f = -; ++C; }
while ('' <= *C && *C <= '') x = (x << ) + (x << ) + *C - '', ++C;
x *= f;
}
inline void fread(long long &x)
{
x = ;
long long f = ;
while (*C < '' || '' < *C) { if(*C == '-') f = -; ++C; }
while ('' <= *C && *C <= '') x = (x << ) + (x << ) + *C - '', ++C;
x *= f;
}
inline void read(int &x)
{
x = ;
int f = ; char c = getchar();
while(c < '' || c > '') { if(c == '-') f = -; c = getchar(); }
while(c >= '' && c <= '') { x = (x << ) + (x << ) + c - ''; c = getchar(); }
x *= f;
}
inline void read(long long &x)
{
x = ;
long long f = ; char c = getchar();
while(c < '' || c > '') { if(c == '-') f = -; c = getchar(); }
while(c >= '' && c <= '') { x = (x << 1ll) + (x << 3ll) + c - ''; c = getchar(); }
x *= f;
}
} using namespace IO;
int rd()
{
int x = , f = ; char c = getchar();
while(c < '' || c > '') { if(c == '-') f = -; c = getchar(); }
while(c >= '' && c <= '') { x = x * + c - ''; c = getchar(); }
return x * f;
}
struct edge {
int nxt, to, w;
} e[N << ];
int n, q, cnt = , root, rt, tot, k;
int head[N], size[N], f[N], Fa[N], dep[N], val[N << ], vis[N], Log[N << ], pos[N << ], mn[N << ][], dis[N];
vector<int> ddis[N], DDis[N];
void link(int u, int v, int w)
{
e[++cnt].nxt = head[u];
head[u] = cnt;
e[cnt].to = v;
e[cnt].w = w;
}
void getroot(int u, int last, int S)
{
f[u] = ;
size[u] = ;
for(int i = head[u]; i; i = e[i].nxt) if(!vis[e[i].to] && e[i].to != last)
{
getroot(e[i].to, u, S);
size[u] += size[e[i].to];
f[u] = max(f[u], size[e[i].to]);
}
f[u] = max(f[u], S - size[u]);
if(f[u] < f[root]) root = u;
}
int getsize(int u, int last)
{
int ret = ;
for(int i = head[u]; i; i = e[i].nxt) if(e[i].to != last && !vis[e[i].to])
ret += getsize(e[i].to, u);
return ret;
}
void divide(int u)
{
vis[u] = ;
for(int i = head[u]; i; i = e[i].nxt) if(!vis[e[i].to])
{
root = ;
getroot(e[i].to, u, getsize(e[i].to, u));
Fa[root] = u;
divide(root);
}
}
void dfs(int u, int last)
{
mn[pos[u] = ++tot][] = dis[u];
for(int i = head[u]; i; i = e[i].nxt) if(e[i].to != last)
{
dis[e[i].to] = dis[u] + e[i].w;
dep[e[i].to] = dep[u] + ;
dfs(e[i].to, u);
mn[++tot][] = dis[u];
}
}
int Dis(int u, int v)
{
int ret = dis[u] + dis[v];
if(pos[u] < pos[v]) swap(u, v);
int x = Log[pos[u] - pos[v] + ];
return ret - * min(mn[pos[v]][x], mn[pos[u] - ( << x) + ][x]);
}
int ask(vector<int> &t, int x)
{
return upper_bound(t.begin(), t.end(), x) - t.begin();
}
int check(int u, int x)
{
int ret = ;
for(int i = u; i; i = Fa[i])
{
int d = ask(ddis[i], x - Dis(u, i));
ret += d;
if(ret > * n) return ret;
}
for(int i = Fa[u]; i; i = Fa[i]) if(Dis(u, i) <= x) ++ret;
for(int i = u; Fa[i]; i = Fa[i])
{
int d = ask(DDis[i], x - Dis(u, Fa[i]));
ret -= d;
}
return ret;
}
int query(int u, int k)
{
int l = , r = 1e9 + , ret = ;
while(r - l > )
{
int mid = (l + r) >> ;
int tmp = check(u, mid);
if(check(u, mid) >= k) r = ret = mid;
else l = mid;
}
return ret;
}
int main()
{
char opt[];
scanf("%s", opt);
read(n);
read(k);
for(int i = ; i < n; ++i)
{
int u, v, w;
read(u);
read(v);
read(w);
link(u, v, w);
link(v, u, w);
}
dfs(, );
for(int i = ; i <= tot; ++i) Log[i] = Log[i >> ] + ;
for(int j = ; j <= ; ++j)
for(int i = ; i + ( << j) - <= tot; ++i)
mn[i][j] = min(mn[i][j - ], mn[i + ( << (j - ))][j - ]);
f[] = 1e9;
getroot(, , getsize(, ));
rt = root;
divide(root);
for(int i = ; i <= n; ++i)
{
for(int j = Fa[i]; j; j = Fa[j]) ddis[j].push_back(Dis(i, j));
for(int j = i; Fa[j]; j = Fa[j]) DDis[j].push_back(Dis(i, Fa[j]));
}
for(int i = ; i <= n; ++i)
{
sort(ddis[i].begin(), ddis[i].end());
sort(DDis[i].begin(), DDis[i].end());
}
for(int i = ; i <= n; ++i) printf("%d\n", query(i, k));
return ;
}
bzoj2117的更多相关文章
- 【BZOJ2117】 [2010国家集训队]Crash的旅游计划
[BZOJ2117] [2010国家集训队]Crash的旅游计划 Description 眼看着假期就要到了,Crash由于长期切题而感到无聊了,因此他决定利用这个假期和好友陶陶一起出去旅游. Cra ...
- BZOJ4317Atm的树&BZOJ2051A Problem For Fun&BZOJ2117[2010国家集训队]Crash的旅游计划——二分答案+动态点分治(点分树套线段树/点分树+vector)
题目描述 Atm有一段时间在虐qtree的题目,于是,他满脑子都是tree,tree,tree…… 于是,一天晚上他梦到自己被关在了一个有根树中,每条路径都有边权,一个神秘的声音告诉他,每个点到其他的 ...
- [BZOJ2051]A Problem For Fun/[BZOJ2117]Crash的旅游计划/[BZOJ4317]Atm的树
[BZOJ2051]A Problem For Fun/[BZOJ2117]Crash的旅游计划/[BZOJ4317]Atm的树 题目大意: 给出一个\(n(n\le10^5)\)个结点的树,每条边有 ...
- BZOJ2117: [2010国家集训队]Crash的旅游计划
裸点分,点分树每层维护有序表,查询二分,复杂度$O(nlog^3n)$. #include<bits/stdc++.h> #define M (u+v>>1) #define ...
- [BZOJ2117]Crash的旅游计划
Description 眼看着假期就要到了,Crash由于长期切题而感到无聊了,因此他决定利用这个假期和好友陶陶一起出去旅游. Crash和陶陶所要去的城市里有N (N > 1) 个景点,Cra ...
随机推荐
- python(35)- 异常处理
一 错误和异常 part1:程序中难免出现错误,而错误分成两种 1.语法错误(这种错误,根本过不了python解释器的语法检测,必须在程序执行前就改正) #语法错误示范一 if #语法错误示范二 ...
- Web框架Django(二)
一.Model 到目前为止,当我们的程序涉及到数据库相关操作时,我们一般都会这么搞: 创建数据库,设计表结构和字段 使用 MySQLdb 来连接数据库,并编写数据访问层代码 业务逻辑层去调用数据访问层 ...
- Google架构学习
http://hideto.iteye.com/blog/130815 原文:Google Architecture Google是伸缩性的王者.Google一直的目标就是构建高性能高伸缩性的基础组织 ...
- CentOS Linux搭建独立SVN Server全套流程(转)
环境为centos6.3 1.首先 看看机器上安装了svn了没有 rpm -qa |grep svn 2.如果没有安装 执行 yum -y install subversion 3.安装好了之后 新建 ...
- Django-ondelete
on_delete=None, # 删除关联表中的数据时,当前表与其关联的field的行为 on_delete=models.CASCADE, # 删除关联数据,与之关联也删除 on_delete=m ...
- SqlServer,Oracle,Mysql 获取指定行数
--sqlserver * FROM dbo.T_TASK --oracle --mysql ,
- vim tips 集锦
删除文件中的空行 :g/^$/d g 表示 global,全文件 ^ 是行开始,$ 是行结束 d 表示删除该 这里只能匹配到没有白空符的空行,假如要删除有空白符的空行,则使用: :g/^\s*$/d ...
- 使用sed来自动注释/恢复crontab中的一个任务
# 注释crontab任务crontab -l > ${WORK_DIR}/cron_binarysed -i 's%\(.*/home/xyz/xyz.sh\)%#\1%' ${WORK ...
- EasyDarwin开源流媒体云平台支持EasyCamera摄像机、EasyCamera手机直播监控、EasyNVR等多终端接入
云平台架构 EasyDarwin开源流媒体云平台目前已经包括了EasyCMS中心管理服务.EasyDarwin流媒体服务.EasyCamera设备端(支持Arm_Linux.Android.PC).E ...
- vmware虚拟机centos网络配置错误,执行/etc/init.d/network start 或 restart 提示Device eth0 has different MAC address than expected, ignoring
vmware虚拟机centos网络配置错误,执行/etc/init.d/network start 或 restart 提示Device eth0 has different MAC address ...