• 【GDKOI2011】反恐任务


    #include <cstdio>
    #include <iostream>
    #define LL long long
    #define RE register
    #define IN inline
    using namespace std;
    const int N = 5e5 + 5;
    int h[N << 1],h1[N],tot,tot1,stk[N],dfn[N << 1],low[N],cnt,dep[N << 1],s[N << 1],f[N << 1][21],n,m,Q,siz,top;
    
    struct edge{
    	int to,nxt;
    }e[N << 2],e1[N << 1];
    void add1(int x,int y)
    {
    	e1[++tot1] = edge{y,h1[x]},h1[x] = tot1;
    	e1[++tot1] = edge{x,h1[y]},h1[y] = tot1;
    }
    void add(int x,int y)
    {
    	e[++tot] = edge{y,h[x]},h[x] = tot;
    	e[++tot] = edge{x,h[y]},h[y] = tot;
    }
    IN void tarjan(int u)
    {
    	dfn[u] = low[u] = ++siz;
    	stk[++top] = u;
    	for (int i = h1[u]; i; i = e1[i].nxt)
    	{
    		int v = e1[i].to;
    		if (!dfn[v]) 
    		{
    			tarjan(v),low[u] = min(low[u],low[v]);
    			if (low[v] == dfn[u])
    			{
    				cnt++,add(cnt,u);
    				for (int x = 0; x != v; top--) x = stk[top],add(cnt,x); 
    			}
    		}
    		else low[u] = min(low[u],dfn[v]); 
    	}
    }
    IN void dfs(int u,int fa)
    {
    	f[u][0] = fa,dfn[u] = ++siz,s[u] = 1,dep[u] = dep[fa] + 1;
    	for (int i = 1; i <= 20; i++)
    		if (f[u][i - 1]) f[u][i] = f[f[u][i - 1]][i - 1];
    		else break;
    	for (int i = h[u]; i; i = e[i].nxt)
    		if (e[i].to != fa) dfs(e[i].to,u),s[u] += s[e[i].to];
    }
    IN int lca(int x,int y)
    {
    	if (dep[x] > dep[y]) swap(x,y);
    	int tmp = dep[y] - dep[x];
    	for (int i = 0; tmp; tmp >>= 1,i++)
    		if (tmp & 1) y = f[y][i];
    	if (x == y) return x;
    	for (int i = 20; i >= 0; i--)
    		if (f[x][i] != f[y][i]) x = f[x][i],y = f[y][i];
    	return f[x][0]; 
    }
    int main() 
    {
    	scanf("%d%d",&n,&m);
    	for (RE int i = 1,q,p; i <= m; i++) scanf("%d%d",&q,&p),add1(q,p);
    	cnt = n,tarjan(1),scanf("%d",&Q),siz = 0,dfs(1,0);
    	for (int ch,x,y,q,p; Q; Q--)
    	{
    		scanf("%d%d%d%d",&ch,&x,&y,&q);
    		int t = lca(x,y);
    		if (ch == 1)
    		{
    			scanf("%d",&p);
    			if (dep[q] < dep[p]) swap(q,p);
    			int k = f[q][0];
    			if (s[k] > s[q] + 1) printf("yes\n");
    			else if (dfn[q] <= dfn[t] && dfn[t] < dfn[q] + s[q]) printf("yes\n");
    				else if ((dfn[q] <= dfn[x] && dfn[x] < dfn[q] + s[q]) || (dfn[q] <= dfn[y] && dfn[y] < dfn[q] + s[q])) printf("no\n");
    					else printf("yes\n");
    		}
    		else
    		{
    			if (t == q) printf("no\n");
    			else if (dfn[q] < dfn[t] && dfn[t] < dfn[q] + s[q]) printf("yes\n");
    				else if ((dfn[q] <= dfn[x] && dfn[x] < dfn[q] + s[q]) || (dfn[q] <= dfn[y] && dfn[y] < dfn[q] + s[q])) printf("no\n");
    					else printf("yes\n");
    		}
    	}
    }
    
  • 相关阅读:
    ABAP接口用法
    监听textarea数值变化
    The first step in solving any problem is recognizing there is one.
    Wrinkles should merely indicate where smiles have been.
    God made relatives.Thank God we can choose our friends.
    Home is where your heart is
    ABAP跳转屏幕
    Python 工具包 werkzeug 初探
    atom通过remote ftp同步本地文件到远程主机的方法
    Mongodb学习笔记一
  • 原文地址:https://www.cnblogs.com/nibabadeboke/p/15839873.html
Copyright © 2020-2023  润新知