CCF 201509-4
使用Tarjan算法,详细文章参考
https://blog.csdn.net/tigerisland45/article/details/54865933
#include <iostream>
#include <queue>
#include <stack>
#include <algorithm>
#include <math.h>
using namespace std;
stack<int> S;
bool vis[100100]={false};
int D[100100]={0},L[1000100];
int index=0;
struct Node{
bool flag=false;
int num;
vector<int> next;
}node[100100];
long long term=0;
long long ans=0;
void tar(int x){
node[x].flag=true;
D[x]=L[x]=++index;
vis[x]=true;
S.push(x);
int l=node[x].next.size();
for(int i=0;i<l;i++){
int k=node[x].next[i];
if(D[k]==0){
tar(k);
L[x]=min(L[x],L[k]);
}else if(vis[k]){
L[x]=min(L[x],D[k]);
}
}
if(D[x]==L[x]){
while(x!=S.top()){
// cout << S.top();
vis[S.top()]=false;
S.pop();
term++;
}
// cout << S.top();
vis[S.top()]=false;
S.pop();
term++;
}
if(term>1){
ans+=term*(term-1)/2;
}
term=0;
}
int main(){
int n,m;
cin >> n >> m;
for(int i=0;i<=n;i++){
node[i].num=i;
node[i].flag=false;
}
for(int i=0;i<m;i++){
int x,y;
cin >> x >> y;
node[x].next.push_back(y);
}
for(int i=1;i<=n;i++){
if(!node[i].flag)
tar(i);
}
cout << ans;
return 0;
}