Submission #737052

#TimeUsernameProblemLanguageResultExecution timeMemory
737052onlk97Duathlon (APIO18_duathlon)C++14
49 / 100
152 ms29852 KiB
#include <bits/stdc++.h>
using namespace std;
long long n,m;
vector <int> g[100010],bc[200010];
bool visited[200010];
long long dfn[100010],lo[100010],w[200020],sz[200020],occ[200020];
int dsu[200020],siz[200020];
int prt(int n){
    if (dsu[n]==n) return n;
    return dsu[n]=prt(dsu[n]);
}
void unn(int u,int v){
    u=prt(u); v=prt(v);
    if (u==v) return;
    if (siz[u]<siz[v]) swap(u,v);
    dsu[v]=dsu[u];
    siz[u]+=siz[v];
}
stack <int> st;
int tme,curid;
void dfs(int cur){
    tme++;
    dfn[cur]=lo[cur]=tme;
    visited[cur]=1;
    st.push(cur);
    for (int i:g[cur]){
        if (!visited[i]){
            dfs(i);
            lo[cur]=min(lo[cur],lo[i]);
            if (lo[i]==dfn[cur]){
                curid++;
                bool ok=1;
                while (ok){
                    bc[st.top()].push_back(curid);
                    bc[curid].push_back(st.top());
                    w[curid]++;
                    if (st.top()==i) ok=0;
                    st.pop();
                }
                bc[cur].push_back(curid);
                bc[curid].push_back(cur);
                w[curid]++;
            }
        } else lo[cur]=min(lo[cur],dfn[i]);
    }
}
int S;
void dfs2(int cur,int prv){
    visited[cur]=1;
    sz[cur]=(cur<=n);
    long long rem=S-(cur<=n);
    occ[cur]=S*(S-1)/2;
    for (int i:bc[cur]){
        if (i==prv) continue;
        dfs2(i,cur);
        sz[cur]+=sz[i];
        occ[cur]-=sz[i]*(sz[i]-1)/2;
        rem-=sz[i];
    }
    occ[cur]-=rem*(rem-1)/2;
}
signed main(){
    cin>>n>>m;
    for (int i=1; i<=2*n; i++){
        dsu[i]=i; siz[i]=(i<=n);
    }
    for (int i=0; i<m; i++){
        int u,v; cin>>u>>v;
        g[u].push_back(v);
        g[v].push_back(u);
        unn(u,v);
    }
    curid=n;
    for (int i=1; i<=n; i++){
        if (!visited[i]) dfs(i);
    }
    for (int i=1; i<=curid; i++) visited[i]=0;
    for (int i=1; i<=n; i++) w[i]=-1;
    for (int i=1; i<=curid; i++){
        if (!visited[i]){
            S=siz[prt(i)];
            dfs2(i,0);
        }
    }
    long long ans=0;
    for (int i=1; i<=curid; i++) ans+=w[i]*occ[i];
    cout<<ans*2<<'\n';
}
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...