带权值得并查集

Building Block

Time Limit : 2000/1000ms (Java/Other)   Memory Limit : 32768/32768K (Java/Other)
Total Submission(s) : 151   Accepted Submission(s) : 57

Font: Times New Roman | Verdana | Georgia

Font Size: ← →

Problem Description

John are playing with blocks. There are N blocks (1 <= N <= 30000) numbered 1...N。Initially, there are N piles, and each pile contains one block. Then John do some operations P times (1 <= P <= 1000000). There are two kinds of operation:

M X Y : Put the whole pile containing block X up to the pile containing Y. If X and Y are in the same pile, just ignore this command. 
C X : Count the number of blocks under block X

You are request to find out the output for each C operation.

Input

The first line contains integer P. Then P lines follow, each of which contain an operation describe above.

Output

Output the count for each C operations in one line.

Sample Input

6
M 1 6
C 1
M 2 4
M 2 6
C 3
C 4

Sample Output

1
0
2

Source

2009 Multi-University Training Contest 1 - Host by TJU

题意:

M x y把x的管放在y管的上面

C x求x的下面有多少个砖块

down[i]表示i到根节点之间有多少块砖,再维护一个sum[x]数组,表示管x上一共串有多少个砖块

find每次更新down数组;

#include<iostream>
#include<stdio.h>
using namespace std;
int par[30005];
int sum[30005];//上面有多少;
int down[30005];
int findi(int x)
{
    if(x==par[x])
        return x;
    int p=findi(par[x]);
    down[x]=down[par[x]]+down[x];
    return par[x]=p;
}
void unioni(int x,int y)
{
    int xx=findi(x);
    int yy=findi(y);
    if(xx!=yy)
    {
        par[xx]=yy;
        down[xx]=sum[yy];
        sum[yy]=sum[yy]+sum[xx];

    }

}

int main()
{
int n;
for(int i=0;i<30005;i++)
    sum[i]=1;
for(int i=0;i<30005;i++)
    down[i]=0;
for(int i=0;i<30005;i++)
     par[i]=i;
scanf("%d",&n);

while(n--)
{
    char a;
    cin>>a;
    if(a==‘M‘)
    {
        int b,c;
       scanf("%d%d",&b,&c);
        unioni(b,c);
    }
    if(a==‘C‘)
    {
        int d;
         scanf("%d",&d);
         findi(d);
         printf("%d\n",down[d]);
    }
}

    return 0;
}
时间: 2024-08-29 05:37:26

带权值得并查集的相关文章

Poj 1182种类(带权)并查集

题目链接 食物链 Time Limit: 1000MS Memory Limit: 10000K Total Submissions: 44316 Accepted: 12934 Description 动物王国中有三类动物A,B,C,这三类动物的食物链构成了有趣的环形.A吃B, B吃C,C吃A. 现有N个动物,以1-N编号.每个动物都是A,B,C中的一种,但是我们并不知道它到底是哪一种. 有人用两种说法对这N个动物所构成的食物链关系进行描述: 第一种说法是"1 X Y",表示X和Y是

POJ 1703:Find them, Catch them(带权的并查集)

Find them, Catch them Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 30702   Accepted: 9447 Description The police office in Tadu City decides to say ends to the chaos, as launch actions to root up the TWO gangs in the city, Gang Dragon

带权值并查集(转)

[POJ 1988] Cube Stacking 我们需要新增两种属性cnt[i]cnt[i]与s[i]s[i],分别表示ii之下的块数和ii所在堆的数量.在路径压缩时,cnt[i] += cnt[f[i]] ,另外在连接操作时,需要动态更新cnt[find(u)]和s[find(v)]的信息. 1 #include <iostream> 2 #define lson l,m,rt<<1 3 #define rson m+1,r,rt<<1|1 4 #define cl

poj 1182 食物链 (带关系的并查集)

  食物链 Time Limit: 1000MS Memory Limit: 10000K Total Submissions: 44835 Accepted: 13069 Description 动物王国中有三类动物A,B,C,这三类动物的食物链构成了有趣的环形.A吃B, B吃C,C吃A. 现有N个动物,以1-N编号.每个动物都是A,B,C中的一种,但是我们并不知道它到底是哪一种. 有人用两种说法对这N个动物所构成的食物链关系进行描述: 第一种说法是"1 X Y",表示X和Y是同类.

UVA - 11987 Almost Union-Find(带删除的并查集)

Almost Union-Find Time Limit: 1000MS   Memory Limit: Unknown   64bit IO Format: %lld & %llu Submit Status Description Problem A Almost Union-Find I hope you know the beautiful Union-Find structure. In this problem, you're to implement something simil

带偏移量的并查集

//带偏移量的并查集≈并查集补集 //维护各点到父节点的距离 可用来分类 #include<iostream> #include<cstdio> #include<cstring> #include<cstdlib> #include<cmath> #include<algorithm> using namespace std; int n,f[1001],d[1001]; int find(int x) { if(x==f[x])

FZU - 2155 - 盟国 (带删除的并查集~~)

Problem 2155 盟国 Accept: 140    Submit: 464 Time Limit: 5000 mSec    Memory Limit : 32768 KB  Problem Description 世界上存在着N个国家,简单起见,编号从0~N-1,假如a国和b国是盟国,b国和c国是盟国,那么a国和c国也是盟国.另外每个国家都有权宣布退盟(注意,退盟后还可以再结盟). 定义下面两个操作: "M X Y" :X国和Y国结盟 "S X" :X国

HDU 3038(权值并查集)

How Many Answers Are Wrong Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 21469    Accepted Submission(s): 7404 Problem Description TT and FF are ... friends. Uh... very very good friends -____

HDU-3038How Many Answers Are Wrong权值并查集

How Many Answers Are Wrong 题意:输入一连串的区间和,问和前面的矛盾个数: 思路:我在做专题,知道是并查集,可是还是不知道怎么做,学了一下权值并查集和大佬的优秀思路,感觉回了一点: 具体就是 在并查集的基础上,加上val[]数组用来记录区间和,而原来的fa[]数组表示的是这个数能到达的最左边的下标: 下面是ac代码 #include <cstdio> #include <algorithm> using namespace std; const int m