zoukankan      html  css  js  c++  java
  • P2342 叠积木 并查集

      

    约翰和贝西在叠积木。共有30000块积木,编号为1到30000。一开始,这些积木放在地上,自然地分成N堆。贝西接受约翰的指示,把一些积木叠在另一些积木的上面。一旦两块积木相叠, 彼此就再也不会分开了,所以最后叠在一起的积木会越来越高。约翰让贝西依次执行P条操作,操作分为两种:

     第一种是移动操作,格式为“移动X到Y的上面”。X和Y代表两块积木的编号,意思是将X所的那堆积木,整体叠放到Y所在的那堆积木之上;

     第二种是统计操作,格式为“统计Z下方的积木数量”。Z代表一块积木的编号,意思是贝西需要报告在编号为Z的积木之下还有多少块积木

    请编写一个程序,帮助贝西回答每条统计问题。

    输入输出格式

    输入格式:

     第一行:单个整数:P,1 ≤ P ≤ 10^5

     第二行到第P + 1行:每行描述一条命令,如果这行开头的字母是 M,代表一条移动命令,后面的两个整数代表上文中的X和Y;如果开头字母是 C,代表一条统计命令。后面的整数代表上文中的Z,保证所有的移动命令都有意义,X和Y不会已经出现在同一堆积木里

    输出格式:

     对每一个统计命令,输出正确回答,用换行符分开每个查询的结果

    输入输出样例

    输入样例#1: 复制
    6
    M 1 6
    C 1
    M 2 4
    M 2 6
    C 3
    C 4
    输出样例#1: 复制
    1
    0
    2


    和银河英雄传几乎一模一样

    唯一有区别的是 输出的是一个点前面的数量 一定要find一次更新一下!!!!


    其他的带权并查集即可
    更新的操作在find1里面要记得!!

    #include<bits/stdc++.h>
    using namespace std;
    //input by bxd
    #define rep(i,a,b) for(int i=(a);i<=(b);i++)
    #define repp(i,a,b) for(int i=(a);i>=(b);--i)
    #define RI(n) scanf("%d",&(n))
    #define RII(n,m) scanf("%d%d",&n,&m)
    #define RIII(n,m,k) scanf("%d%d%d",&n,&m,&k)
    #define RS(s) scanf("%s",s);
    #define ll long long
    #define REP(i,N)  for(int i=0;i<(N);i++)
    #define CLR(A,v)  memset(A,v,sizeof A)
    //////////////////////////////////
    #define inf 0x3f3f3f3f
    const int N=1e6;
    int f[N],cnt[N],d[N],a,b;
    char s[3];
    int find1(int x)
    {
        if(x==f[x])return x;
        int k=find1(f[x]);
        d[x]+=d[f[x]];
        return f[x]=k;
    }
    void union1(int a,int b)//a放到b后面
    {
        int x=find1(a),y=find1(b);
        d[x]+=cnt[y];
        f[x]=y;
        cnt[y]+=cnt[x];
        cnt[x]=0;
    }
    int main()
    {
        int n;RI(n);
        rep(i,1,30000+5)f[i]=i,cnt[i]=1,d[i]=0;
    
        rep(i,1,n)
        {
            RS(s);
            if(s[0]=='M')
            {
                RII(a,b);
                union1(a,b);
            }
            else
            {
                RI(a);
                int k=find1(a);//这条其实很关键
                cout<<d[a]<<endl;
            }
        }
        return 0;
    }
    View Code
    
    
  • 相关阅读:
    BZOJ 1597: [Usaco2008 Mar]土地购买
    BZOJ 1005: [HNOI2008]明明的烦恼
    BZOJ 1004: [HNOI2008]Cards
    Burnside引理和Polya定理
    BZOJ 1003: [ZJOI2006]物流运输
    BZOJ 1002: [FJOI2007]轮状病毒
    BZOJ 1001: [BeiJing2006]狼抓兔子
    网络流 最大流dinic算法解释
    51nod 1299 监狱逃离
    2017.11.26【清华集训2017】模拟
  • 原文地址:https://www.cnblogs.com/bxd123/p/10937833.html
Copyright © 2011-2022 走看看