zoukankan      html  css  js  c++  java
  • 【块状树】【博弈论】bzoj3729 Gty的游戏

    块状树,每个块的根记录一下当前块内距块根为奇数距离的异或和和偶数距离的异或和,询问的时候讨论一下即可。

    总的节点数可能超过50000。

    #include<cstdio>
    #include<cmath>
    using namespace std;
    #define N 100001
    int n,m,L,a[N];
    int en,v[N<<1],next[N<<1],first[N];
    int e2,v2[N<<1],nex2[N<<1],firs2[N];
    int sz,top[N],siz[N],fa[N],xorv[2][N],meiz,dep[N];
    void AddEdge(int U,int V)
    {
    	v[++en]=V;
    	next[en]=first[U];
    	first[U]=en;
    }
    void AddEdg2(int U,int V)
    {
    	v2[++e2]=V;
    	nex2[e2]=firs2[U];
    	firs2[U]=e2;
    }
    void makeblock(int U)
    {
    	for(int i=first[U];i;i=next[i])
    	  if(v[i]!=fa[U])
    	    {
    	      fa[v[i]]=U;
    	      dep[v[i]]=dep[U]+1;
    	      if(siz[top[U]]<sz)
    	        {
    	          ++siz[top[U]];
    	          top[v[i]]=top[U];
    	        }
    	      makeblock(v[i]);
    	    }
    }
    void makeGoto(int U)
    {
        for(int i=first[U];i;i=next[i])
          if(v[i]!=fa[U])
            {
              if(top[v[i]]!=top[U])
                AddEdg2(top[U],v[i]);
              makeGoto(v[i]);
            }
    }
    void dfs_init(int U,bool d)
    {
    	xorv[d][top[U]]^=a[U];
    	for(int i=first[U];i;i=next[i])
    	  if(v[i]!=fa[U]&&top[v[i]]==top[U])
    	    dfs_init(v[i],d^1);
    }
    int ans;
    void dfs_Goto(int U,bool d)
    {
    	ans^=xorv[d][top[U]];
    	for(int i=firs2[U];i;i=nex2[i])
    	  dfs_Goto(v2[i],d^((dep[v2[i]]-dep[U])&1));
    }
    void dfs_block(int U,bool d)
    {
    	if(d) ans^=a[U];
    	for(int i=first[U];i;i=next[i])
    	  if(v[i]!=fa[U])
    	    {
    	      if(top[v[i]]==top[U])
    	        dfs_block(v[i],d^1);
    	      else
    	        dfs_Goto(v[i],d);
    	    }
    }
    void query(int U)
    {
    	ans=0;
    	if(U==top[U]) dfs_Goto(U,1);
    	else dfs_block(U,0);
    }
    void Update(int U,int x)
    {
    	xorv[0][top[U]]=xorv[1][top[U]]=0;
    	a[U]=x%(L+1);
    	dfs_init(top[U],0);
    }
    void AddNode(int U,int V,int x)
    {
    	++n;
    	fa[V]=U;
    	dep[V]=dep[U]+1;
    	if(siz[top[U]]<sz)
          {
            top[V]=top[U];
            ++siz[top[V]];
          }
        else
          {
            top[V]=V;
            siz[V]++;
            AddEdg2(top[U],V);
          }
        AddEdge(U,V);
        a[V]=x%(L+1);
        xorv[(dep[V]-dep[top[V]])&1][top[V]]^=a[V];
    }
    int main()
    {
    	int x,y,c,op;
    	scanf("%d%d",&n,&L);
    	for(int i=1;i<=n;++i)
    	  {
    	  	scanf("%d",&a[i]);
    	  	top[i]=i;
    	  	siz[i]=1;
    	  	a[i]%=(L+1);
    	  }
    	for(int i=1;i<n;++i)
    	  {
    	  	scanf("%d%d",&x,&y);
    	  	AddEdge(x,y);
    	  	AddEdge(y,x);
    	  }
    	sz=sqrt(n);
    	makeblock(1);
    	makeGoto(1);
    	for(int i=1;i<=n;++i)
    	  if(top[i]==i)
    	    dfs_init(i,0);
    	scanf("%d",&m);
    	for(;m;--m)
    	  {
    	  	scanf("%d%d",&op,&x); x^=meiz;
    	  	if(op==1)
    	  	  {
    	  	  	query(x);
    	  	  	if(ans)
    	  	  	  {
    	  	  	  	++meiz;
    	  	  	  	puts("MeiZ");
    	  	  	  }
    	  	  	else puts("GTY");
    	  	  }
    	  	else if(op==2)
    	  	  {
    	  	  	scanf("%d",&c); c^=meiz;
    	  	  	Update(x,c);
    	  	  }
    	  	else
    	  	  {
    	  	  	scanf("%d%d",&y,&c); y^=meiz; c^=meiz;
    	  	  	AddNode(x,y,c);
    	  	  }
    	  }
    	return 0;
    }
  • 相关阅读:
    Elasticsearch 6.x版本全文检索学习之数据建模
    Elasticsearch 6.x版本全文检索学习之集群调优建议
    Elasticsearch 6.x版本全文检索学习之聚合分析入门
    SpringCloud的入门学习之Eureka(高可用注册中心HA)构建Provider服务、Consumer服务
    SpringCloud的入门学习之Netflix-eureka(Eureka的集群版搭建)
    Elasticsearch 6.x版本全文检索学习之Search的运行机制
    ERP入门
    NoSQL数据库介绍
    傅立叶变换的物理意义
    电容的基础知识
  • 原文地址:https://www.cnblogs.com/autsky-jadek/p/4340971.html
Copyright © 2011-2022 走看看