题解原网 https://blog.csdn.net/qty2001/article/details/77133189
图论的一道好题
#include<bits/stdc++.h>
#define N 605
#define M 200050
#define inf 0x7fffffff
using namespace std;
int first[N],next[M],to[M],w[M],tot;
int dis[N][N],n,m1,m2,ans; vector<int> scc[N];
int dfn[N],low[N],sta[N],insta[N],top,sign,sum;
void add(int x,int y,int z){
next[++tot]=first[x],first[x]=tot,to[tot]=y,w[tot]=z;
}
void dfs(int u){
dfn[u]=low[u]=++sign;
sta[++top]=u,insta[u]=1;
for(int i=first[u];i;i=next[i]){
int t=to[i];
if(!dfn[t]) dfs(t),low[u]=min(low[u],low[t]);
else if(insta[t]&&dfn[t]<low[u]) low[u]=dfn[t];
}
if(low[u]==dfn[u]){
sum++; do{
insta[sta[top]]=0;
scc[sum].push_back(sta[top]);
}while(sta[top--]!=u);
}
}
int main(){
scanf("%d%d%d",&n,&m1,&m2);
for(int i=1;i<=N-1;i++) for(int j=1;j<=N-1;j++) dis[i][j]=-inf;
for(int i=1;i<=m1;i++){
int x,y; scanf("%d%d",&x,&y);
add(x,y,1),add(y,x,-1);
dis[x][y]=max(dis[x][y],1),dis[y][x]=max(dis[y][x],-1);
}
for(int i=1;i<=m2;i++){
int x,y; scanf("%d%d",&x,&y);
add(x,y,0); dis[x][y]=max(dis[x][y],0);
}
for(int i=1;i<=n;i++) if(!dfn[i]) dfs(i);
for(int now=1;now<=sum;now++){
int siz = scc[now].size();
for(int k=0;k<siz;k++){ int c = scc[now][k];
for(int i=0;i<siz;i++){ int a = scc[now][i];
for(int j=0;j<siz;j++){ int b = scc[now][j];
if(dis[a][c]==-inf || dis[c][b]==-inf) continue;
dis[a][b] = max(dis[a][b],dis[a][c]+dis[c][b]);
}
}
}
int tmp=0;
for(int i=0;i<siz;i++){
for(int j=0;j<siz;j++){
int a = scc[now][i],b = scc[now][j];
if(dis[a][b]!=-inf) tmp=max(tmp,abs(dis[a][b]));
}
} ans += tmp+1;
for(int i=0;i<siz;i++){
int a = scc[now][i];
if(dis[a][a]>0) {printf("NIE"); return 0;}
}
} printf("%d",ans); return 0;
}