zoukankan      html  css  js  c++  java
  • bzoj 2243

    链剖,线段树记录左右端点即可

    区间合并的顺序还是要注意一下,挺容易乱。。

      1 #include<bits/stdc++.h>
      2 #define inc(i,l,r) for(i=l;i<=r;i++)
      3 #define dec(i,l,r) for(i=l;i>=r;i--)
      4 #define link(x) for(edge *j=h[x];j;j=j->next)
      5 #define mem(a) memset(a,0,sizeof(a))
      6 #define inf 1e9
      7 #define ll long long
      8 #define succ(x) (1<<x)
      9 #define NM 100000+5
     10 using namespace std;
     11 int read(){
     12     int x=0,f=1;char ch=getchar();
     13     while(!isdigit(ch)){if(ch=='-')f=-1;ch=getchar();}
     14     while(isdigit(ch))x=x*10+ch-'0',ch=getchar();
     15     return x*f;
     16 }
     17 struct info{
     18     int s,l,r,z;
     19 }T[8*NM],null;
     20 struct edge{
     21     int t;
     22     edge *next;
     23 }e[2*NM],*h[NM],*p=e;
     24 int n,m,f[NM],son[NM],id[NM],_id[NM],a[NM],d[NM],top[NM],TOP,size[NM],tot;
     25 int _x,_y,_v,l,r;
     26 info operator+(const info&x,const info&y){
     27     info f;
     28     if(x.s==-1)return y;
     29     if(y.s==-1)return x;
     30     f.l=x.l;f.r=y.r;
     31     f.s=x.s+y.s;
     32     if(x.r==y.l)f.s--;
     33     f.z=-1;
     34     return f;
     35 }
     36 void add(int x,int y){
     37     p->t=y;p->next=h[x];h[x]=p;p++;
     38 }
     39 void dfs1(int x){
     40     link(x)
     41     if(!f[j->t]){
     42         f[j->t]=x;
     43         d[j->t]=d[x]+1;
     44         dfs1(j->t);
     45         size[x]+=size[j->t];
     46         if(size[j->t]>size[son[x]])son[x]=j->t;
     47     }
     48     size[x]++;
     49 }
     50 void dfs2(int x){
     51     top[x]=TOP;id[x]=++tot;_id[tot]=x;
     52     if(son[x])dfs2(son[x]);
     53     link(x)
     54     if(!top[j->t])dfs2(TOP=j->t);
     55 }
     56 void pushdown(int i){
     57     if(T[i].z>=0){
     58         T[i<<1].s=T[i<<1|1].s=1;
     59         T[i<<1].l=T[i<<1].r=T[i<<1|1].l=T[i<<1|1].r=T[i].z;
     60         T[i<<1].z=T[i<<1|1].z=T[i].z;
     61         T[i].z=-1;
     62     }
     63 }
     64 void build(int i,int x,int y){
     65     int t=x+y>>1;
     66     if(x==y){
     67         T[i].s=1;T[i].z=-1;
     68         T[i].l=T[i].r=a[_id[x]];
     69         return;
     70     }
     71     build(i<<1,x,t);build(i<<1|1,t+1,y);
     72     T[i]=T[i<<1]+T[i<<1|1];
     73 }
     74 void ch(int i,int x,int y){
     75     int t=x+y>>1;
     76     if(l<=x&&y<=r){
     77         T[i].s=1;T[i].l=T[i].r=_v;T[i].z=_v;
     78         return;
     79     }
     80     if(l>y||r<x)return;
     81     pushdown(i);
     82     ch(i<<1,x,t);ch(i<<1|1,t+1,y);
     83     T[i]=T[i<<1]+T[i<<1|1];
     84 }
     85 info query(int i,int x,int y){
     86     int t=x+y>>1;
     87     if(l<=x&&y<=r)return T[i];
     88     if(y<l||r<x)return null;
     89     pushdown(i);
     90     return query(i<<1,x,t)+query(i<<1|1,t+1,y);
     91 }
     92 int main(){
     93     int i;
     94     n=read();m=read();
     95     inc(i,1,n)a[i]=read();
     96     inc(i,1,n-1){
     97         _x=read();_y=read();
     98         add(_x,_y);add(_y,_x);
     99     }
    100     f[1]=1;null.s=-1;
    101     dfs1(1);
    102     dfs2(TOP=1);
    103     build(1,1,n);
    104     while(m--){
    105         char opt[10];
    106         info tx=null,ty=null;
    107         scanf("%s",opt);_x=read();_y=read();
    108         if(opt[0]=='C'){
    109             _v=read();
    110             while(top[_x]!=top[_y]){
    111                 if(d[top[_x]]<d[top[_y]])swap(_x,_y);
    112                 l=id[top[_x]];r=id[_x];
    113                 ch(1,1,n);
    114                 _x=f[top[_x]];
    115             }
    116             if(d[_x]>d[_y])swap(_x,_y);
    117             l=id[_x];r=id[_y];
    118             ch(1,1,n);
    119         }else{
    120             while(top[_x]!=top[_y])
    121             if(d[top[_x]]>d[top[_y]]){
    122                 l=id[top[_x]];r=id[_x];
    123                 tx=query(1,1,n)+tx;
    124                 _x=f[top[_x]];
    125             }else{
    126                 l=id[top[_y]];r=id[_y];
    127                 ty=query(1,1,n)+ty;
    128                 _y=f[top[_y]];
    129             }
    130             swap(ty.l,ty.r);swap(tx.l,tx.r);
    131             if(d[_x]<d[_y]){
    132                 l=id[_x];r=id[_y];
    133                 tx=tx+query(1,1,n);
    134             }else{
    135                 l=id[_y];r=id[_x];
    136                 ty=ty+query(1,1,n);
    137             }
    138             swap(ty.l,ty.r);
    139             tx=tx+ty;
    140             printf("%d
    ",tx.s);
    141         }
    142     }
    143     return 0;
    144 }
    View Code
  • 相关阅读:
    Android 压力测试工具Monkey
    解决maven的依赖总是无法下载完成
    JDBC连接数据库(二)
    JDBC连接数据库(一)
    webdriver js点击无法点击的元素
    多线程Java面试题总结
    PHP unset销毁变量并释放内存
    ThinkPHP函数详解:D方法
    PHP 函数:intval()
    ThinkPHP 模板显示display和assign的用法
  • 原文地址:https://www.cnblogs.com/onlyRP/p/5042377.html
Copyright © 2011-2022 走看看