• CF343D Water Tree


    题目链接

    题目翻译(摘自洛谷)

    疯狂科学家Mike培养了一颗有根树,由n个节点组成。每个节点是一个要么装满水要么为空的贮水容器. 树的节点用1~n编号,其中根节点为1.对于每个节点的容器,其子节点的容器均在这一容器下方,并且每个节点都由一根可以向下流水的管道与其子节点连接. Mike想要对这棵树做以下操作:
    1将节点v注满水. 这样v和其子节点都会充满水.
    2将节点v置空. 这样v及其祖先节点(从v到根节点的路径)都会被置空.
    3查询当前节点v是否充满水.
    初始时,所有节点都为空. Mike已经制定好了他的操作顺序. 在对树进行实验前,他决定先模拟一下操作. 请你帮助Mike得出他操作后的结果.

    思路

    裸树链剖分,区间修改,单点查询。

      1 #include<iostream>
      2 #include<cstdio>
      3 using namespace std;
      4 const int N=500005;
      5 int n,cnt,dcnt,hd[N];
      6 struct edge
      7 {
      8     int to,nxt;
      9 }v[2*N];
     10 struct node
     11 {
     12     int fa,son,sz,dep,tp,s,e;
     13 }tr[N];
     14 struct segtree
     15 {
     16     int l,r,stat,tag;
     17 }st[4*N];
     18 void addedge(int x,int y)
     19 {
     20     v[++cnt].to=y;
     21     v[cnt].nxt=hd[x];
     22     hd[x]=cnt;
     23 }
     24 void dfs1(int u)
     25 {
     26     tr[u].sz=1;
     27     for(int i=hd[u];i;i=v[i].nxt)
     28         if(v[i].to!=tr[u].fa)
     29         {
     30             tr[v[i].to].fa=u;
     31             tr[v[i].to].dep=tr[u].dep+1;
     32             dfs1(v[i].to);
     33             tr[u].sz+=tr[v[i].to].sz;
     34             if(tr[v[i].to].sz>tr[tr[u].son].sz)
     35                 tr[u].son=v[i].to;
     36         }
     37 }
     38 void dfs2(int u,int top)
     39 {
     40     tr[u].tp=top;
     41     tr[u].s=++dcnt;
     42     if(tr[u].son)
     43     {
     44         dfs2(tr[u].son,top);
     45         for(int i=hd[u];i;i=v[i].nxt)
     46             if(v[i].to!=tr[u].fa&&v[i].to!=tr[u].son)
     47                 dfs2(v[i].to,v[i].to);
     48     }
     49     tr[u].e=dcnt;
     50 }
     51 void build(int num,int l,int r)
     52 {
     53     st[num].l=l,st[num].r=r;
     54     st[num].tag=-1;
     55     if(l==r)
     56         return ;
     57     int mid=(l+r)/2;
     58     build(2*num,l,mid),build(2*num+1,mid+1,r);
     59 }
     60 void pushdown(int num)
     61 {
     62     if(st[num].tag!=-1)
     63     {
     64         if(st[num].l!=st[num].r)
     65         {
     66             st[2*num].stat=st[2*num+1].stat=st[num].tag;
     67             st[2*num].tag=st[2*num+1].tag=st[num].tag;
     68         }
     69         st[num].tag=-1;
     70     }
     71 }
     72 void change(int num,int l,int r,int z)
     73 {
     74     if(l>st[num].r||r<st[num].l)
     75         return ;
     76     if(st[num].l>=l&&st[num].r<=r)
     77     {
     78         st[num].tag=st[num].stat=z;
     79         return ;
     80     }
     81     pushdown(num);
     82     change(2*num,l,r,z),change(2*num+1,l,r,z);
     83 }
     84 int query(int num,int x)
     85 {
     86     if(st[num].l>x||st[num].r<x)
     87         return 0;
     88     if(st[num].l==st[num].r)
     89         return st[num].stat;
     90     pushdown(num);
     91     return query(2*num,x)+query(2*num+1,x);
     92 }
     93 void fnd(int x)
     94 {
     95     int f1=tr[x].tp;
     96     while(f1!=1)
     97     {
     98         change(1,tr[f1].s,tr[x].s,0);
     99         x=tr[f1].fa,f1=tr[x].tp;
    100     }
    101     change(1,1,tr[x].s,0);
    102 }
    103 int main()
    104 {
    105     scanf("%d",&n);
    106     for(int i=1;i<=n-1;i++)
    107     {
    108         int x,y;
    109         scanf("%d%d",&x,&y);
    110         addedge(x,y),addedge(y,x);
    111     }
    112     dfs1(1);
    113     dfs2(1,1);
    114     build(1,1,n);
    115     int q,x,y;
    116     scanf("%d",&q);
    117     while(q--)
    118     {
    119         scanf("%d%d",&x,&y);
    120         switch(x)
    121         {
    122             case 1:
    123                 change(1,tr[y].s,tr[y].e,1);
    124                 break;
    125             case 2:
    126                 fnd(y);
    127                 break;
    128             case 3:
    129                 printf("%d
    ",query(1,tr[y].s));
    130                 break;
    131         }
    132     }
    133     return 0;
    134 }
  • 相关阅读:
    第三周学习进度条
    软件工程个人作业02
    构建之法阅读笔记02
    学习进度条
    构建之法阅读笔记01
    软件工程个人作业01
    构建之法粗读
    第一次作业
    动手动脑接口与继承
    大道至简第七章第八章
  • 原文地址:https://www.cnblogs.com/fantasquex/p/9355715.html
Copyright © 2020-2023  润新知