無向圖的深度和廣度優先遍歷 - C++

無向圖的深度和廣度優先遍歷 - C++

標籤(空格分隔): 算法


本文來自《啊哈!算法》第5章第1節 點擊下載PDF文件查看

需要解決的問題

一個無向圖,怎麼從深度和廣度來遍歷這個圖,也就是怎麼個走法

需要了解和學習的點

  • 圖的鄰接矩陣存儲法(就是一個二維數組
  • 回溯 (這裏要理解循環能給遞歸產生回溯的效果
  • 圖的生成樹

代碼

深度優先遍歷

/**
 * 圖的深度優先遍歷
 * 啊哈算法 P131
 * by jtahstu at 2017-09-14
 */

#include <iostream>
#include <climits>

using namespace std;
int book[101] = {0}, sum, n, m, e[101][101] = {0};

void dfs(int cur) {
    cout << cur << " ";
    sum++;
    if (sum == n)return;
    for (int i = 1; i <= n; i++) {  //循環達到回溯的效果
        if (book[i] == 0 && e[cur][i] == 1) {
            book[i] = 1;
            dfs(i);
        }
    }
    return;
}

int main(int argc, const char *argv[]) {
    cin >> n >> m;  //n個節點,m條邊
    for (int i = 1; i <= n; i++)    //初始化
        for (int j = 1; j <= n; j++) {
            if (i == j)
                e[i][j] = 0;
            else
                e[i][j] = INT_MAX;
        }
    int a, b;
    for (int k = 1; k <= m; k++) {  //矩陣表示
        cin >> a >> b;
        e[a][b] = 1;
        e[b][a] = 1;
    }
    book[1] = 1;
    dfs(1);

    return 0;
}
/**
5 4
3 2
3 4
2 5
2 1

5 5
1 2
1 3
1 5
2 4
3 5
*/

廣度優先遍歷

/**
 * 圖的廣度優先遍歷
 * 啊哈算法 P134
 * by jtahstu at 2017-09-14
 */

#include <iostream>
#include <climits>

using namespace std;

int main() {
    int n, m, a, b, cur, book[101] = {0}, e[101][101] = {0};
    int que[101], head = 1, tail = 1;

    cin >> n >> m; //n個節點,m條邊
    for (int i = 1; i <= n; i++)   //初始化
        for (int j = 1; j <= n; j++) {
            if (i == j)
                e[i][j] = 0;
            else
                e[i][j] = INT_MAX;
        }
    for (int i = 1; i <= m; i++) {  //圖的矩陣表示
        cin >> a >> b;
        e[a][b] = 1;
        e[b][a] = 1;
    }

    que[1] = 1;
    tail++;
    book[1] = 1;  //走過的標記爲1
    while (head < tail) {
        cur = que[head];
        for (int i = 1; i <= n; i++) { //當前頂點往下的所有可能都存到隊列中去
            if (book[i] == 0 && e[cur][i] == 1) {
                que[tail] = i;
                tail++;
            }
            if (tail > n)
                break;
        }
        head++; //表示當前點遍歷結束,下個點
    }

    for (int i = 1; i <= n; i++) {
        cout << que[i] << " ";
    }

    return 0;
}

/**
5 4
1 3
1 5
3 2
5 4
 */
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章