Codeforecs Round #425 D Misha, Grisha and Underground (倍增LCA)
2 seconds
256 megabytes
standard input
standard output
Misha and Grisha are funny boys, so they like to use new underground. The underground has n stations connected with n - 1 routes so that each route connects two stations, and it is possible to reach every station from any other.
The boys decided to have fun and came up with a plan. Namely, in some day in the morning Misha will ride the underground from station sto station f by the shortest path, and will draw with aerosol an ugly text "Misha was here" on every station he will pass through (including sand f). After that on the same day at evening Grisha will ride from station t to station f by the shortest path and will count stations with Misha's text. After that at night the underground workers will wash the texts out, because the underground should be clean.
The boys have already chosen three stations a, b and c for each of several following days, one of them should be station s on that day, another should be station f, and the remaining should be station t. They became interested how they should choose these stations s, f, t so that the number Grisha will count is as large as possible. They asked you for help.
The first line contains two integers n and q (2 ≤ n ≤ 105, 1 ≤ q ≤ 105) — the number of stations and the number of days.
The second line contains n - 1 integers p2, p3, ..., pn (1 ≤ pi ≤ n). The integer pi means that there is a route between stations pi and i. It is guaranteed that it's possible to reach every station from any other.
The next q lines contains three integers a, b and c each (1 ≤ a, b, c ≤ n) — the ids of stations chosen by boys for some day. Note that some of these ids could be same.
Print q lines. In the i-th of these lines print the maximum possible number Grisha can get counting when the stations s, t and f are chosen optimally from the three stations on the i-th day.
题意:
对于一个终点站f, 从s出发,和从t出发。经过的相同站有多少
有n个点,n-1条边。m次询问给出3个数 a, b, c。在a, b, c中选择一个终点两个起点,使得共同的站最大。
题解:
由于是一个树,所以就直接建树(点到点的距离设置为1)。暴力跑a,b, c分别为终点的情况。
现在讨论a 为顶点的情况。
那么公共的站点就是公共距离+1。
#include <iostream>
#include <cstdio>
#include <cstring>
#include <string>
#include <algorithm>
#include <cmath>
#include <vector>
#include <queue>
#include <map>
#include <stack>
#include <set>
using namespace std;
typedef long long LL;
typedef unsigned long long uLL;
#define ms(a, b) memset(a, b, sizeof(a))
#define pb push_back
#define mp make_pair
const LL INF = 0x7fffffff;
const int inf = 0x3f3f3f3f;
const int mod = 1e9+;
const int maxn = +;
const int DEG = ;
struct node
{
int to, next;
int w;
}edge[*maxn];
int head[maxn], tol, flag[maxn];
void init() {
tol = ;
ms(head, -);
ms(flag, );
}
void addedge(int u, int v, int w)
{
edge[tol].to = v;
edge[tol].next = head[u];
edge[tol].w = w;
head[u] = tol++;
}
int fa[maxn][DEG];
int DD[maxn];
int deg[maxn];
void bfs(int root)
{
queue<int> que;
deg[root] = ;
fa[root][] = root;
DD[root] = ;
que.push(root);
while(!que.empty()){
int tmp = que.front();
que.pop();
for(int i = ;i<DEG;i++){
fa[tmp][i] = fa[fa[tmp][i-]][i-];
}
for(int i = head[tmp];i!=-;i=edge[i].next){
int v = edge[i].to;
if(v == fa[tmp][]) continue;
deg[v] = deg[tmp]+;
fa[v][] = tmp;
DD[v] = DD[tmp]+edge[i].w;
que.push(v);
}
}
}
int LCA(int u, int v){
int ans = ;
if(deg[u]>deg[v]) swap(u, v);
int hu = deg[u], hv = deg[v];
int tu = u, tv = v;
for(int det = hv - hu, i=;det;det>>=, i++){
if(det&){
tv = fa[tv][i];
}
}
if(tu==tv){
return tu;
}
for(int i = DEG - ;i>=;i--){
if(fa[tu][i] == fa[tv][i]) continue;
tu = fa[tu][i];
tv = fa[tv][i];
}
return fa[tu][];
}
int DIS(int u, int v)
{
return DD[u] + DD[v] - *DD[LCA(u, v)];
}
void solve()
{
int n, q;
cin >> n >> q;
for(int i = ;i<=n;i++){
int x;cin >> x;
addedge(i, x, );
addedge(x, i, );
flag[x] = ;
}
int root;
for(int i = ;i<=n;i++){
if(!flag[i]){
root = i;
break;
}
}
// cout << root << endl;
bfs(root);
for(int i = ;i<q;i++){
int a, b, c;
cin >> a >> b >> c;
int ans = ;
ans = max(ans, (DIS(b, a)+DIS(c, a)-DIS(b, c))/);
ans = max(ans, (DIS(a, b)+DIS(c, b)-DIS(a, c))/);
ans = max(ans, (DIS(a, c)+DIS(b, c)-DIS(a, b))/);
cout << ans+ << endl;
}
}
int main() {
#ifdef LOCAL
freopen("input.txt", "r", stdin);
// freopen("output.txt", "w", stdout);
#endif
ios::sync_with_stdio();
cin.tie();
init();
solve();
}
Codeforecs Round #425 D Misha, Grisha and Underground (倍增LCA)的更多相关文章
- Codeforces Round #425 (Div. 2) Misha, Grisha and Underground(LCA)
Misha, Grisha and Underground time limit per test 2 seconds memory limit per test 256 megabytes inpu ...
- Codeforces 832D: Misha, Grisha and Underground 【LCA模板】
题目链接 模板copy from http://codeforces.com/contest/832/submission/28835143 题意,给出一棵有n个结点的树,再给出其中的三个结点 s,t ...
- Codeforces 832D - Misha, Grisha and Underground
832D - Misha, Grisha and Underground 思路:lca,求两个最短路的公共长度.公共长度公式为(d(a,b)+d(b,c)-d(a,c))/2. 代码: #includ ...
- Codeforces 832 D Misha, Grisha and Underground
Misha, Grisha and Underground 题意:Misha 和 Grisha 是2个很喜欢恶作剧的孩子, 每天早上 Misha 会从地铁站 s 通过最短的路到达地铁站 f, 并且在每 ...
- D. Misha, Grisha and Underground 树链剖分
D. Misha, Grisha and Underground 这个题目算一个树链剖分的裸题,但是这个时间复杂度注意优化. 这个题目可以选择树剖+线段树,时间复杂度有点高,比较这个本身就有n*log ...
- Codeforces Round #425 (Div. 2) Problem D Misha, Grisha and Underground (Codeforces 832D) - 树链剖分 - 树状数组
Misha and Grisha are funny boys, so they like to use new underground. The underground has n stations ...
- Codeforces Round #425 (Div. 2) D.Misha, Grisha and Underground
我奇特的脑回路的做法就是 树链剖分 + 树状数组 树状数组是那种 区间修改,区间求和,还有回溯的 当我看到别人写的是lca,直接讨论时,感觉自己的智商收到了碾压... #include<cmat ...
- 【树链剖分】【dfs序】【LCA】【分类讨论】Codeforces Round #425 (Div. 2) D. Misha, Grisha and Underground
一棵树,q次询问,每次给你三个点a b c,让你把它们选做s f t,问你把s到f +1后,询问f到t的和,然后可能的最大值是多少. 最无脑的想法是链剖线段树……但是会TLE. LCT一样无脑,但是少 ...
- 【 Codeforces Round #425 (Div. 2) D】Misha, Grisha and Underground
[Link]:http://codeforces.com/contest/832/problem/D [Description] 给你一棵树; 然后给你3个点 让你把这3个点和点s,t,f对应; 然后 ...
随机推荐
- 《好久不见》(Cover 陈奕迅)箫声远 洞箫
Your browser does not support the audio element.
- Layerui 弹出层的位置设置
距顶 offset: '300px' 例1: layer.msg("请先选择项!", { offset: '300px' });例2: layer.confirm("确定 ...
- python之设置windows背景图片
#!/usr/bin/env python3 # -*- coding: utf-8 -*- __author__ = 'jiangwenwen' from PIL import Image impo ...
- Mybatis-基本步骤
1.1Mybatis框架概述 Mybatis是基于Java的持久层框架,内部封装了jdbc,使开发者只需关注sql语句本身,而不需要花费精力去处理加载驱动.创建连接.创建Statement等繁杂的过程 ...
- [2019杭电多校第五场][hdu6628]permutation 1
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=6628 题意为求字典序第k小的差异数组,差异数组p满足p[i]=a[i+1]-a[i]. 头铁的爆搜,因 ...
- 三连击 P1008 洛谷 python写法
三连击 P1008 洛谷 题意 将\(1,2, \cdots,9\)共9个数分成3组,分别组成3个三位数,且使这3个三位数构成1:2:3的比例,试求出所有满足条件的3个三位数. 解题思路 这里我使用了 ...
- [BZOJ2588]Count on a tree(LCA+主席树)
题面 给定一棵N个节点的树,每个点有一个权值,对于M个询问(u,v,k),你需要回答u xor lastans和v这两个节点间第K小的点权.其中lastans是上一个询问的答案,初始为0,即第一个询问 ...
- SpringMVC处理器拦截器 Interceptor
拦截器概念 Java 里的拦截器是动态拦截action调用的对象.它提供了一种机制可以使开发者可以定义在一个action执行的前后执行的代码,也可以在一个action执行前阻止其执行,同时也提供了一种 ...
- vue 跳转页面返回时tab状态有误的解决办法
一.前言 最近在做新vue项目的时候遇到了一个问题,就是tab间的切换没有问题,当跳转到其他页面时,且这个页面并非子路由,再用浏览器的返回按钮返回首页时,tab的active始终指向默认的第一个选项. ...
- P1828 香甜的黄油 (spfa)
[题目描述] 农夫John知道每只奶牛都在各自喜欢的牧场(一个牧场不一定只有一头牛).给出各头牛在的牧场和牧场间的路线,找出使所有牛到达的路程和最短的牧场(他将把糖放在那). [题目链接] https ...