原题链接:https://www.luogu.org/problem/show?pid=1983
题目大意:每个车站有一个权值,每一车次始发站与终点站之间如果有不停靠的点,那么它的权值一定比停靠的点的权值都要小。
处理完m条线路后,能够得到一系列的大小关系,于是就可以通过拓扑排序求出结果。
几个需要注意的地方:有的边可能已经被加过一次,所以最好用邻接矩阵存边,避免点的度数被重复加。
#include<cstdio> #include<algorithm> #include<cstring> using namespace std; void read(int &y) { y=0;char x=getchar(); while(x<'0'||x>'9') x=getchar(); while(x>='0'&&x<='9') { y=y*10+x-'0'; x=getchar(); } } int n,m,x,ans,top; int p[1005],d[1005],l[1005]; int e[1005][1005],st[1005]; bool b[1005],vis[1005]; int main() { read(n);read(m); for(int i=1;i<=m;i++) { memset(b,0,sizeof(b)); read(x); for(int j=1;j<=x;j++) { read(p[j]); b[p[j]]=1; } for(int j=p[1];j<=p[x];j++) { if(b[j]!=0) continue; for(int k=1;k<=x;k++) { if(e[j][p[k]]!=0) continue; e[j][p[k]]=1; d[p[k]]++; } } } top=0; for(int i=1;i<=n;i++) { if(d[i]==0) { st[++top]=i; l[i]=1; } } for(int i=1;i<=top;i++) { for(int j=1;j<=n;j++) { if(e[st[i]][j]==0) continue; e[st[i]][j]=0; d[j]--; if(d[j]==0) { l[j]=l[st[i]]+1; ans=max(ans,l[j]); st[++top]=j; } } } printf("%d",ans); return 0; }