分析数据,使用邻接表来存储图。拓扑排序适用于有向无环图(Directed Acyclic Graph简称DAG)。因此出现环就是“-1”的情况。
其中实现邻接表有两种方式:
1.使用数组来实现邻接表
#include <queue>
#include <stdio.h>
#include <string.h>
#include <iostream>
#include <algorithm>
using namespace std;
const int MAX = 10010;
int n,m;
int into[MAX],head[MAX],M[MAX],tot,sum,ans;
struct reward{//边的结构定义
int to;
int next;
}edge[MAX<<1];
void toposort(){
queue <int> Q;
for(int i=1; i<=n; i++)
if(!into[i]) Q.push(i);
while(!Q.empty()){
int u = Q.front();
sum += M[u];
Q.pop();
ans++;
for(int i=head[u]; i!=-1; i=edge[i].next){
int v = edge[i].to;
if(--into[v] == 0){
Q.push(v);
M[v] = M[u] + 1;
}
}
}
}
int main(){
while(scanf("%d%d",&n,&m) == 2){
memset(head, -1, sizeof(head));
memset(into, 0, sizeof(into));
for(int i=1; i<=n; i++)
M[i] = 888;
tot = 0,sum = 0,ans = 0;
while(m--){
int a,b;
scanf("%d%d",&a,&b);
edge[tot].to = a;
edge[tot].next = head[b];
head[b] = tot++;
into[a]++;
}
toposort();
if(ans != n) sum = -1;
printf("%d\n",sum);
}
return 0;
}
2.使用vector来实现邻接表
#include <queue>
#include <vector>
#include <stdio.h>
#include <string.h>
#include <iostream>
#include <algorithm>
using namespace std;
const int MAX = 10010;
int n,m;
int into[MAX],head[MAX],M[MAX],tot,sum,ans;
vector <int> vt[MAX];
void toposort(){
queue <int> Q;
for(int i=1; i<=n; i++)
if(!into[i]) Q.push(i);
while(!Q.empty()){
int u = Q.front();
sum += M[u];
Q.pop();
ans++;
for(int i=0; i<vt[u].size(); i++){
int v = vt[u][i];
if(--into[v] == 0){
Q.push(v);
M[v] = M[u] + 1;
}
}
}
}
int main(){
while(scanf("%d%d",&n,&m) == 2){
memset(head, -1, sizeof(head));
memset(into, 0, sizeof(into));
for(int i=1; i<=n; i++){
M[i] = 888;
vt[i].clear();
}
tot = 0,sum = 0,ans = 0;
while(m--){
int a,b;
scanf("%d%d",&a,&b);
vt[b].push_back(a);
into[a]++;
}
toposort();
if(ans != n) sum = -1;
printf("%d\n",sum);
}
return 0;
}