题目链接
题意:给出n个点,m条有向边,每个点不小于888,每条边的弧尾大于弧头。求最小和。
反向建图,拓扑排序。
#include<cstdio> #include<cmath> #include<cstring> #include<iostream> #define N 11000 #define M 22000 using namespace std; struct node { int next,to; }e[M]; int in[N],head[N],n,m,num[N],cnt; void add_edge(int u,int v) { e[cnt].to=v; e[cnt].next=head[u]; head[u]=cnt++; in[v]++; } int toposort() { int k=0,ans=0; while(k<n) { int flag=1; for(int i=1;i<=n;i++) { if(in[i]==0) { in[i]--; k++; ans+=num[i]; for(int j=head[i];j+1;j=e[j].next) { int u=e[j].to; num[u]=max(num[u],num[i]+1); in[u]--; } flag=0; } } if(flag) return -1; } return ans; } int main() { while(~scanf("%d%d",&n,&m)) { memset(head,-1,sizeof(head)); memset(in,0,sizeof(in)); for(int i=1;i<=n;i++) num[i]=888; cnt=0; for(int i=0;i<m;i++) { int u,v; scanf("%d%d",&u,&v); add_edge(v,u); } cout<<toposort()<<endl; } }