• poj3237 Tree


    题目链接:...G20过了再补

    题目大意:

    三种操作:
    CHANGE i v:改变第i条边的值
    NEGATE a b:将a到b路径上的边取绝对值
    QUERY a b:询问a到b路径上边的最大值


    题解:当,,,就树剖..(LCT线段树也可以貌似

    调了很久还能说什么orz更新什么的要及时

    p.s.范围开大TLE开小RE。。

    #include<cstdio>
    #include<cstdlib>
    #include<cstring>
    #include<iostream>
    #include<algorithm>
    using namespace std;
    #define maxn 20100
    #define INF 0x7fffffff
    
    struct node
    {
    	int x,y,c,next;
    }a[maxn*2],e[maxn];
    int len,first[maxn];
    struct tree
    {
    	int l,r,lc,rc,rev,mxx,mnn;
    }tr[maxn];int trlen;
    int mymax(int x,int y){return (x>y)?x:y;}
    int mymin(int x,int y){return (x<y)?x:y;}
    void ins(int x,int y)
    {
    	len++;//a[len].c=c;
    	a[len].x=x;a[len].y=y;
    	a[len].next=first[x];first[x]=len;
    }
    int son[maxn],fa[maxn],dep[maxn];
    int z,tot[maxn],top[maxn],ys[maxn];
    void dfs1(int x)
    {
    	tot[x]=1;son[x]=0;
    	for (int k=first[x];k!=-1;k=a[k].next)
    	{
    		int y=a[k].y;
    		if (y!=fa[x])
    		{
    			dep[y]=dep[x]+1;
    			fa[y]=x;
    			dfs1(y);
    			if (tot[son[x]]<tot[y]) son[x]=y;
    			tot[x]+=tot[y];
    		}
    	}
    }
    void dfs2(int x,int tp)
    {
    	ys[x]=++z;top[x]=tp;
    	if (son[x]!=0) dfs2(son[x],tp);
    	for (int k=first[x];k!=-1;k=a[k].next)
    	{
    		int y=a[k].y;
    		if (y!=fa[x] && y!=son[x]) dfs2(y,y);
    	}
    }
    void bt(int l,int r)
    {
    	trlen++;int now=trlen;
    	tr[now].l=l;tr[now].r=r;
    	tr[now].lc=tr[now].rc=-1;
    	tr[now].rev=0;
    	tr[now].mnn=INF;tr[now].mxx=-INF;
    	if (l<r)
    	{
    		int mid=(l+r)>>1;
    		tr[now].lc=trlen+1;bt(l,mid);
    		tr[now].rc=trlen+1;bt(mid+1,r);
    	}
    }
    void swop(int &x,int &y)
    {
    	int tt=x;x=y;y=tt;
    }
    void updata(int now,int lc,int rc)
    {
    	if (tr[now].rev)
    	{
    		if (lc!=0)
    		{
    			swop(tr[lc].mxx,tr[lc].mnn);
    			tr[lc].mxx=-tr[lc].mxx;
    			tr[lc].mnn=-tr[lc].mnn;
    			tr[lc].rev^=1;
    		}
    		if (rc!=0)
    		{
    			swop(tr[rc].mxx,tr[rc].mnn);
    			tr[rc].mxx=-tr[rc].mxx;
    			tr[rc].mnn=-tr[rc].mnn;
    			tr[rc].rev^=1;
    		}tr[now].rev=0;
    	}
    }
    void change(int now,int x,int k)
    {
    	if (tr[now].l==tr[now].r) 
    	{
    		tr[now].mxx=tr[now].mnn=k;
    		tr[now].rev=0;return;
    	}int lc=tr[now].lc,rc=tr[now].rc,mid=(tr[now].l+tr[now].r)>>1;
    	updata(now,lc,rc);
    	if (x<=mid) change(lc,x,k);
    	else change(rc,x,k);
    	tr[now].mxx=mymax(tr[lc].mxx,tr[rc].mxx);
    	tr[now].mnn=mymin(tr[lc].mnn,tr[rc].mnn);
    }
    int findmx(int now,int l,int r)
    {
    	if (tr[now].l==l && tr[now].r==r) return tr[now].mxx;
    	int lc=tr[now].lc,rc=tr[now].rc,mid=(tr[now].l+tr[now].r)>>1;
    	updata(now,lc,rc);
    	if (r<=mid) return findmx(lc,l,r);
    	else if (l>mid) return findmx(rc,l,r);
    	else return mymax(findmx(lc,l,mid),findmx(rc,mid+1,r));
    }
    void fanz(int now,int l,int r)
    {
    	if (tr[now].l==l && tr[now].r==r)
    	{
    		swop(tr[now].mxx,tr[now].mnn);
    		tr[now].mxx=-tr[now].mxx;
    		tr[now].mnn=-tr[now].mnn;
    		tr[now].rev^=1;return;
    	}
    	int lc=tr[now].lc,rc=tr[now].rc,mid=(tr[now].l+tr[now].r)>>1;
    	updata(now,lc,rc);
    	if (r<=mid) fanz(lc,l,r);
    	else if (l>mid) fanz(rc,l,r);
    	else fanz(lc,l,mid),fanz(rc,mid+1,r);
    	tr[now].mxx=mymax(tr[lc].mxx,tr[rc].mxx);
    	tr[now].mnn=mymin(tr[lc].mnn,tr[rc].mnn);
    }
    int query(int x,int y)
    {
    	int tx=top[x],ty=top[y],ans=-INF;
    	while (tx!=ty)
    	{
    		if (dep[tx]>dep[ty])
    		{
    			swop(x,y);
    			swop(tx,ty);
    		}ans=mymax(ans,findmx(1,ys[ty],ys[y]));
    		y=fa[ty];ty=top[y];
    	}
    	if (x==y) return ans;
    	else
    	{
    		if (dep[x]>dep[y]) swop(x,y);
    		return mymax(ans,findmx(1,ys[son[x]],ys[y]));
    	}
    }
    void reverse(int x,int y)
    {
    	int tx=top[x],ty=top[y];
    	while (tx!=ty)
    	{
    		if (dep[tx]>dep[ty])
    		{
    			swop(x,y);
    			swop(tx,ty);
    		}fanz(1,ys[ty],ys[y]);
    		y=fa[ty];ty=top[y];
    	}
    	if (x==y) return;
    	else
     	{
    		if (dep[x]>dep[y]) swop(x,y);
    		fanz(1,ys[son[x]],ys[y]);
    	}
    }
    int main()
    {
    	//freopen("a.in","r",stdin);
    	//freopen("a.out","w",stdout);
    	int T,i,n,x,y,c;char s[20];
    	scanf("%d",&T);
    	while (T--)
    	{
    		scanf("%d",&n);
    		len=0;memset(first,-1,sizeof(first));
    		for (i=1;i<n;i++)
    		{
    			scanf("%d%d%d",&x,&y,&c);
    			ins(x,y);ins(y,x);
    			e[i].x=x;e[i].y=y;e[i].c=c;
    		}
    		dep[1]=0;fa[1]=0;dfs1(1);
    		z=0;dfs2(1,1);
    		trlen=0;bt(1,z);
    		for (i=1;i<n;i++) 
    		{
    			if (dep[e[i].x]>dep[e[i].y])
    			{
    				int tt=e[i].x;
    				e[i].x=e[i].y;
    				e[i].y=tt;
    			}
    			change(1,ys[e[i].y],e[i].c);
    		}
    		while (1)
    		{
    			scanf("
    %s",s);
    			if (s[0]=='Q')
    			{
    				scanf("%d%d",&x,&y);
    				printf("%d
    ",query(x,y));
    			}else if (s[0]=='C')
    			{
    				scanf("%d%d",&x,&y);
    				change(1,ys[e[x].y],y);
    			}else if (s[0]=='N')
    			{
    				scanf("%d%d",&x,&y);
    				reverse(x,y);
    			}else if (s[0]=='D') break;
    		}
    	}
    	return 0;
    }


  • 相关阅读:
    JSON学习笔记
    Java面试题之对static的理解
    【知了堂学习笔记】java基础知识之继承
    【知了堂学习笔记】多态基本知识
    Final关键字
    子父类构造函数特点
    原来学编程这么简单,如何理解程序的本质(今天听了【遇见狂神说】发布的《从HelloWorld到程序本质的思考》这个视频,有了自己的一些感悟,在这里和大家做一个分享)
    浅谈c3p0连接池和dbutils工具类的使用
    Mysql数据库重要知识点
    Express安装与调试
  • 原文地址:https://www.cnblogs.com/Euryale-Rose/p/6527872.html
Copyright © 2020-2023  润新知