輸入:第一行為點數n和各連接邊數m
接下來m行寫某一條有向邊的起始點和終止點
輸出:拓撲排序所有方案和方案種數
sample input
9 10 0 1 1 3 2 4 3 2 3 6 5 4 6 5 7 5 8 6 8 7
sample output
0 1 3 2 8 6 7 5 4 0 1 3 2 8 7 6 5 4 0 1 3 8 2 6 7 5 4 0 1 3 8 2 7 6 5 4 0 1 3 8 6 2 7 5 4 0 1 3 8 6 7 2 5 4 0 1 3 8 6 7 5 2 4 0 1 3 8 7 2 6 5 4 0 1 3 8 7 6 2 5 4 0 1 3 8 7 6 5 2 4 0 1 8 3 2 6 7 5 4 0 1 8 3 2 7 6 5 4 0 1 8 3 6 2 7 5 4 0 1 8 3 6 7 2 5 4 0 1 8 3 6 7 5 2 4 0 1 8 3 7 2 6 5 4 0 1 8 3 7 6 2 5 4 0 1 8 3 7 6 5 2 4 0 1 8 7 3 2 6 5 4 0 1 8 7 3 6 2 5 4 0 1 8 7 3 6 5 2 4 0 8 1 3 2 6 7 5 4 0 8 1 3 2 7 6 5 4 0 8 1 3 6 2 7 5 4 0 8 1 3 6 7 2 5 4 0 8 1 3 6 7 5 2 4 0 8 1 3 7 2 6 5 4 0 8 1 3 7 6 2 5 4 0 8 1 3 7 6 5 2 4 0 8 1 7 3 2 6 5 4 0 8 1 7 3 6 2 5 4 0 8 1 7 3 6 5 2 4 0 8 7 1 3 2 6 5 4 0 8 7 1 3 6 2 5 4 0 8 7 1 3 6 5 2 4 8 0 1 3 2 6 7 5 4 8 0 1 3 2 7 6 5 4 8 0 1 3 6 2 7 5 4 8 0 1 3 6 7 2 5 4 8 0 1 3 6 7 5 2 4 8 0 1 3 7 2 6 5 4 8 0 1 3 7 6 2 5 4 8 0 1 3 7 6 5 2 4 8 0 1 7 3 2 6 5 4 8 0 1 7 3 6 2 5 4 8 0 1 7 3 6 5 2 4 8 0 7 1 3 2 6 5 4 8 0 7 1 3 6 2 5 4 8 0 7 1 3 6 5 2 4 8 7 0 1 3 2 6 5 4 8 7 0 1 3 6 2 5 4 8 7 0 1 3 6 5 2 4 sum:52
代碼:
1 #include <iostream> 2 #include <cstring> 3 #include <cstdio> 4 using namespace std; 5 int n,m; 6 int s[100][100]; //鄰接矩陣,用於保存圖的結構 7 int visit[100]; //頂點標志 8 int indegree[100]; //各個頂點的入度 9 int ans[100]; 10 int sum=0; //記錄拓撲排序總數 11 void DFS(int num) //num記錄當前已經訪問的頂點個數 12 { 13 int i,j,k; 14 if (num==n){ //訪問完n個頂點代表這是一條新的可走的拓撲路徑 15 sum++; //路徑總數加1 16 for (i=0;i<n;i++) 17 printf("%d ",ans[i]); 18 printf("\n"); 19 return; 20 } 21 22 for (i=0;i<n;i++){ 23 if ((!indegree[i])&&(!visit[i])){ //如果頂點i入度為0且沒有被訪問過 24 for (j=0;j<n;j++){ 25 if (s[i][j]) indegree[j]--; //遍歷所有和它連接的點並且斷開聯系(即點的入度減1) 26 } 27 28 visit[i]=1; //該入度為0的點標記訪問過 29 ans[num]=i; //儲存值 30 DFS(num+1); //以訪問點數+1 31 32 for (k=0;k<n;k++){ //回溯,恢復現場,將入度重新加一,並且將該頂點標記為未訪問 33 if (s[i][k]) indegree[k]++; 34 } 35 visit[i]=0; //回溯標志 方便下一次for循環使用 36 //ans沒有必要回溯,因為后續的值可以直接覆蓋 37 } 38 } 39 return; 40 } 41 42 int main(){ 43 int a,b,i,j,num; 44 scanf("%d%d",&n,&m); 45 memset(indegree,0,sizeof(indegree)); 46 memset(s,0,sizeof(s)); 47 memset(visit,0,sizeof(visit)); 48 memset(ans,0,sizeof(ans)); 49 50 for (i=1;i<=m;i++){ 51 scanf("%d%d",&a,&b); 52 s[a][b]=1; 53 indegree[b]++; 54 } 55 56 DFS(0); 57 cout<<"sum:"<<sum; 58 return 0; 59 }