中国MOOC大学_数据结构与算法实战_周强_辛酸解题二

P10 推断学生所属学校的人数 (15 分)
某个比赛现场有来自不同学校的N名学生,给出M对“两人同属一所学校”的关系, 请推断学校数量,并找出人数最多的学校。

输入格式:
第一行是一个在[2, 1000]范围的整数N

接下来N行,每行是一个在现场的学生的姓名,每个姓名仅由字母组成,长度不超过30

接下来一行是非负整数M,表示有M对关系;

然后是M行,每行是用空格间隔的两个人名,表示同属一所学校。

输出格式:
在一行内分别输出学校的数量以及人数最多学校的人数,用一个空格分隔。

输入样例:

8
Bill
Ellen
Ann
Chris
Daisy
Flin
Henry
Grace
5
Ann Chris
Ellen Chris
Daisy Flin
Henry Ellen
Grace Flin

输出样例:

3 4

上代码
并查集基本查找的题

#include <iostream>
#include <queue>
#include <set>
#include <map>
using namespace std;
template<class T>
struct DisjointSet{
   
    int *parent;
    T *data;
    set<T> *mates;
    int capacity;
    int size;
    map<T,int> m;
    DisjointSet(int max=10){
   
        capacity = max;
        size = 0;
        parent = new int[max+1];
        data = new T[max+1];
        mates = new set<T>[max+1];
    }
    ~DisjointSet(){
   
        delete [] parent;
        delete [] data;
    }
    bool insert(T x){
   
        if(size==capacity)return false;

         data[++size]=x;
         parent[size]=-1;
         mates[size].insert(x);
         m[x]=size;
         return true;
    }
    int find(T x){
   
        typename map<T,int>::iterator it;
        it = m.find(x);
        if(it == m.end())return -1;
        int rt,i;
        i=rt = it->second;
       while(parent[rt]>0)
           rt= parent[rt];
       int tmp;
       for(;i!=rt;i=tmp)
       {
   
           tmp = parent[i];
           parent[i] = rt;
       }
        return rt;

    }
    void unionSet(T x,T y){
   
        int rx,ry;
        rx = find(x);
        ry = find(y);
        if(rx==-1 || ry ==-1)return;
        if(rx == ry)return;
        if(parent[rx]<parent[ry]){
   
            parent[rx] +=parent[ry];
            parent[ry] = rx;
            mates[rx].insert(mates[ry].begin(),mates[ry].end());
            mates[ry].clear();
        }
        else{
   
            parent[ry] +=parent[rx];
            parent[rx]=ry;
            mates[ry].insert(mates[rx
  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值