【题解】P6680 [CCO2019] Marshmallow Molecules

P6680

题意

一个 \(n\)\(m\) 边的图,图无重边,无自环。

满足这样一条性质:如果三边互不相等,则三边可以构成三角形。

思路

思路简单,用集合的思想来做。

引用一下 K0stlin 大佬的性质:题目中的操作等价于将一个点大于某个儿子的儿子们赋给这个儿子(这里的儿子表示这个点有出边连向的点)。你发现把这些儿子全都赋给当前最小的儿子也是正确的,因为这样儿子集合一定会遍历完。

于是就可以将一个点的儿子所在集合合并到另外一个儿子所在的集合中。

可以用神奇的 STL —— set 来维护,不知道 set 的点

AC Code

#include <bits/stdc++.h>
using namespace std;
int n,m;
set<int> s[100001];
int main() {
	cin>>n>>m;
    for(int i=1,x,y;i<=m;++i) {
        cin>>x>>y;
        s[x].insert(y);
    }
    long long ans=0;
    for(int i=1,p;i<=n;++i) {
        if(s[i].empty()) continue;
        s[i].erase(i);
        ans+=s[i].size();
        p=(*s[i].begin());
        if(s[i].size()>s[p].size())swap(s[i],s[p]);
        while(!s[i].empty()) {
            s[p].insert(*s[i].begin());
            s[i].erase(s[i].begin());
        }
    }
    cout<<ans;
    return 0;
}
posted @ 2024-04-06 18:01  Kcjhfqr  阅读(37)  评论(0)    收藏  举报
.poem-wrap { position: relative; width: 1000px; max-width: 80%; border: 2px solid #797979; border-top: none; text-align: center; margin: 40px auto; } .poem-left { left: 0; } .poem-right { right: 0; } .poem-border { position: absolute; height: 2px; width: 27%; background-color: #797979; } .poem-wrap p { width: 70%; margin: auto; line-height: 30px; color: #797979; } .poem-wrap h1 { position: relative; margin-top: -20px; display: inline-block; letter-spacing: 4px; color: #797979; font-size: 2em; margin-bottom: 20px; } #poem_sentence { font-size: 25px; } #poem_info { font-size: 15px; margin: 15px auto; }