传送门


弱化版

考虑到去掉一个点使得存在两个点不连通的形式类似割点,不难想到建立圆方树。那么在圆方树上对于给出的关键点建立虚树之后,我们需要求的就是虚树路径上所有圆点的数量减去关键点的数量。

因为没有DP,所以其实没有必要将虚树建立起来,只需要维护一个链并就可以了。

#include<bits/stdc++.h>
//This code is written by Itst
using namespace std; inline int read(){
int a = 0;
char c = getchar();
bool f = 0;
while(!isdigit(c) && c != EOF){
if(c == '-')
f = 1;
c = getchar();
}
if(c == EOF)
exit(0);
while(isdigit(c)){
a = a * 10 + c - 48;
c = getchar();
}
return f ? -a : a;
} const int MAXN = 2e5 + 7;
int head[MAXN] , N , M , cnt , cntEd , ans;
int dfn[MAXN] , low[MAXN] , st[MAXN] , ts , top;
int ind[MAXN] , dep[MAXN] , TS;
vector < int > ch[MAXN];
int num[MAXN] , jump[MAXN][19];
struct Edge{
int end , upEd;
}Ed[MAXN << 1];
struct cmp{
bool operator ()(int a , int b){
return ind[a] < ind[b];
}
};
set < int , cmp > s;
set < int , cmp > :: iterator it1 , it2; inline void addEd(int a , int b){
Ed[++cntEd].end = b;
Ed[cntEd].upEd = head[a];
head[a] = cntEd;
} void pop(int x , int bot){
++cnt;
ch[cnt].clear();
ch[x].push_back(cnt);
do{
ch[cnt].push_back(st[top]);
}while(st[top--] != bot);
} void tarjan(int x , int p){
dfn[x] = low[x] = ++ts;
st[++top] = x;
ch[x].clear();
for(int i = head[x] ; i ; i = Ed[i].upEd)
if(Ed[i].end != p)
if(!dfn[Ed[i].end]){
tarjan(Ed[i].end , x);
low[x] = min(low[x] , low[Ed[i].end]);
if(low[Ed[i].end] >= dfn[x])
pop(x , Ed[i].end);
}
else
low[x] = min(low[x] , dfn[Ed[i].end]);
} void dfs(int x , int p){
ind[x] = ++TS;
dep[x] = dep[p] + 1;
jump[x][0] = p;
for(int i = 1 ; i <= 18 ; ++i)
jump[x][i] = jump[jump[x][i - 1]][i - 1];
num[x] = num[p] + (x <= N);
for(int i = 0 ; i < ch[x].size() ; ++i)
dfs(ch[x][i] , x);
} inline int LCA(int x , int y){
if(dep[x] < dep[y])
swap(x , y);
for(int i = 18 ; i >= 0 ; --i)
if(dep[x] - (1 << i) >= dep[y])
x = jump[x][i];
if(x == y)
return x;
for(int i = 18 ; i >= 0 ; --i)
if(jump[x][i] != jump[y][i]){
x = jump[x][i];
y = jump[y][i];
}
return jump[x][0];
} inline void insert(int x){
s.insert(x);
it1 = it2 = s.find(x);
int p = 0 , q = 0;
if(it1 != s.begin())
p = LCA(*(--it1) , x);
if(++it2 != s.end())
q = LCA(*it2 , x);
p = dep[p] < dep[q] ? q : p;
ans += num[x] - num[p];
} int main(){
#ifndef ONLINE_JUDGE
freopen("in","r",stdin);
freopen("out","w",stdout);
#endif
for(int T = read() ; T ; --T){
cnt = N = read();
M = read();
memset(head , 0 , sizeof(head));
memset(dfn , 0 , sizeof(dfn));
cntEd = ts = TS = top = 0;
for(int i = 1 ; i <= M ; ++i){
int a = read() , b = read();
addEd(a , b);
addEd(b , a);
}
tarjan(1 , 0);
dfs(1 , 0);
for(int Q = read() ; Q ; --Q){
s.clear();
ans = 0;
int S = read() , t;
for(int i = 1 ; i <= S ; ++i){
int a = read();
if(i == 1)
t = a;
else
if(t != 1)
t = LCA(t , a);
insert(a);
}
printf("%d\n" , ans - S - num[jump[t][0]]);
}
}
return 0;
}

Luogu4606 SDOI2018 战略游戏 圆方树、虚树、链并的更多相关文章

  1. bzoj5315/luoguP4517 [SDOI2018]战略游戏(圆方树,虚树)

    bzoj5315/luoguP4517 [SDOI2018]战略游戏(圆方树,虚树) bzoj Luogu 题目描述略(太长了) 题解时间 切掉一个点,连通性变化. 上圆方树. $ \sum |S| ...

  2. [SDOI2018]战略游戏 圆方树,树链剖分

    [SDOI2018]战略游戏 这题是道路相遇(题解)的升级版,询问的两个点变成了\(S\)个点. LG传送门 还是先建出圆方树,考虑对于询问的\(S\)个点,答案就是圆方树上能包含这些点的最小连通块中 ...

  3. BZOJ5329:[SDOI2018]战略游戏(圆方树,虚树)

    Description 省选临近,放飞自我的小Q无心刷题,于是怂恿小C和他一起颓废,玩起了一款战略游戏. 这款战略游戏的地图由n个城市以及m条连接这些城市的双向道路构成,并且从任意一个城市出发总能沿着 ...

  4. BZOJ.5329.[SDOI2018]战略游戏(圆方树 虚树)

    题目链接 显然先建圆方树,方点权值为0圆点权值为1,两点间的答案就是路径权值和减去起点终点. 对于询问,显然可以建虚树.但是只需要计算两关键点间路径权值,所以不需要建出虚树.统计DFS序相邻的两关键点 ...

  5. Luogu P4606 [SDOI2018] 战略游戏 圆方树 虚树

    https://www.luogu.org/problemnew/show/P4606 把原来的图的点双联通分量缩点(每个双联通分量建一个点,每个割点再建一个点)(用符合逻辑的方式)建一棵树(我最开始 ...

  6. 【SDOI2018】战略游戏(同时普及虚树)

    先看一道虚树普及题:给你一棵 $n$ 个点的树,$m$ 次询问,每次询问给你 $k$ 个关键点,求把这些点都连起来的路径并的最短长度.$1\le n,m\le 100000,\space 1\le \ ...

  7. [SDOI2018]战略游戏(圆方树+虚树)

    喜闻乐见的圆方树+虚树 图上不好做,先建出圆方树. 然后答案就是没被选到的且至少有两条边可以走到被选中的点的圆点的数量. 语文不好,但结论画画图即可得出. 然后套路建出虚树. 发现在虚树上DP可以得出 ...

  8. 仙人掌 && 圆方树 && 虚树 总结

    仙人掌 && 圆方树 && 虚树 总结 Part1 仙人掌 定义 仙人掌是满足以下两个限制的图: 图完全联通. 不存在一条边处在两个环中. 其中第二个限制让仙人掌的题做 ...

  9. [BZOJ5329][SDOI2018]战略游戏

    bzoj luogu Description 省选临近,放飞自我的小Q无心刷题,于是怂恿小C和他一起颓废,玩起了一款战略游戏. 这款战略游戏的地图由n个城市以及m条连接这些城市的双向道路构成,并且从任 ...

随机推荐

  1. mysql 之库, 表的简易操作

    一. 库的操作 1.创建数据库 创建数据库: create database 库名 charset utf8;   charset uft8  可选项 1.2 数据库命名规范: 可以由字母.数字.下划 ...

  2. vue 父子组件互相传值容易出现的报错

    对于父子组件之间的互相传值,报错如下: [Vue warn]: Avoid mutating a prop directly since the value will be overwritten w ...

  3. 转:drupal常用api

    drupal常用api   最短的函数 // 语言字串,除了可以获取对应语言外,还可以设置字串变量.可以是!var, @var或 %var,%var就添加元素外层.@var会过滤HTML,!var会原 ...

  4. Android学习笔记----Java字符串MD5加密

    代码如下: /** * MD5单向加密,32位,用于加密密码,因为明文密码在信道中传输不安全,明文保存在本地也不安全 * * @param str * @return */ public static ...

  5. (网页)angular中实现li或者某个元素点击变色的两种方法(转)

    转自脚本之家: 本篇文章主要介绍了angular中实现li或者某个元素点击变色的两种方法,非常具有实用价值,需要的朋友可以参考下 本文介绍了angular中实现li或者某个元素点击变色的两种方法,分享 ...

  6. webrtc学习: 部署stun和turn服务器

    webrtc的P2P穿透部分是由libjingle实现的. 步骤顺序大概是这样的: 1. 尝试直连. 2. 通过stun服务器进行穿透 3. 无法穿透则通过turn服务器中转. stun 服务器比较简 ...

  7. entity framework异常 The specified cast from a materialized 'System.Int32' type to the 'System.String' type is not valid

    ROW_NUMBER() OVER (ORDER BY (select Null)) AS Id entity framework 查询中有这句会有异常

  8. 使用Tampermonkey(油猴) 插件,重新实现了,百度搜索热点过滤功能

    昨天晚上,花了点时间学习了Chrome插件的制作方法,并书写了<Chrome 百度搜索热点过滤插件 - 开源软件>这一文章,简单地介绍自己实现的百度搜索热点过滤神器的原理和使用方式,并进行 ...

  9. 基于python的快速傅里叶变换FFT(二)

    基于python的快速傅里叶变换FFT(二)本文在上一篇博客的基础上进一步探究正弦函数及其FFT变换. 知识点  FFT变换,其实就是快速离散傅里叶变换,傅立叶变换是数字信号处理领域一种很重要的算法. ...

  10. My strength (C-A-R)

    My strength: I am good at problem resolving Challenge In the first year when I come to America I pas ...