AtCoder Beginner Contest 378 ——F

昊天djh發表於2024-11-07

https://atcoder.jp/contests/abc378/tasks/abc378_f
https://atcoder.jp/contests/abc378/editorial/11307

#include<bits/stdc++.h>
#define x first
#define y second
#define all(x) (x).begin(),(x).end()
#define lowbit(x) (x)&-(x)
using namespace std;
typedef long long ll;
typedef pair<ll,ll> pii;
const int N=2e5+10,mod=1e9+7;
ll n,m,k;
int u[N],v[N],d[N],p[N],cnt[N];
int find(int x){
    if(p[x]!=x) p[x]=find(p[x]);
    return p[x];
}
void unit(int a,int b){
    a=find(a),b=find(b);
    p[a]=b;
}
void solve(){
    cin>>n;
    for(int i=1;i<n;i++){
        cin>>u[i]>>v[i];
        d[u[i]]++,d[v[i]]++;
    }
    for(int i=1;i<=n;i++) p[i]=i;
    for(int i=1;i<n;i++){
        if(d[u[i]]==d[v[i]]&&d[u[i]]==3) unit(u[i],v[i]);//度是3且相鄰的放入一個集合中
        else if(d[u[i]]==2&&d[v[i]]==3) cnt[v[i]]++;//記錄度是3的點相鄰的度是2的點有多少個
        else if(d[u[i]]==3&&d[v[i]]==2) cnt[u[i]]++;
    }
    map<int,set<int>> p;
    for(int i=1;i<n;i++){
        if(d[u[i]]==3) p[find(u[i])].insert(u[i]);
        if(d[v[i]]==3) p[find(v[i])].insert(v[i]);
    }
    //cout<<d[9]<<' '<<d[4]<<' '<<d[1]<<' '<<d[11]<<endl;
    ll res=0;
    //cout<<p.size()<<endl;
    for(auto [u,v]:p){
        ll c=0;
        for(int x:v){
            c+=cnt[x];
            //cout<<x<<endl;
        }
        //cout<<c<<endl;
        res+=c*(c-1)/2;
    }
    cout<<res<<endl;
}
int main(){
    ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);

    int _=1;
    //cin>>_;
    while(_--) solve();

    return 0;
}

相關文章