Data Structure and Algorithm http staff ustc edu

  • Slides: 60
Download presentation
Data Structure and Algorithm 《数据结构及其算法》 http: //staff. ustc. edu. cn/~dongeliu/dsa. html 刘 东 信息学院

Data Structure and Algorithm 《数据结构及其算法》 http: //staff. ustc. edu. cn/~dongeliu/dsa. html 刘 东 信息学院 6系 中国科学技术大学

 • 邻接矩阵法的实现 const int MAX_VERTEX_NUM = 20; // 图的类型:有向图、有向网、无向图、无向网 typedef enum {DG, DN,

• 邻接矩阵法的实现 const int MAX_VERTEX_NUM = 20; // 图的类型:有向图、有向网、无向图、无向网 typedef enum {DG, DN, UDG, UDN} Graph. Kind; typedef struct { // Vertex. Type表示顶点的类型,例如char、int…… Vertex. Type vexs[MAX_VERTEX_NUM]; // Arc. Type表示边和权值的类型 // 若为无权图,可取bool型 // 若为网,可取int型、float型…… Arc. Type arcs[MAX_VERTEX_NUM]; int vexnum, arcnum; Graph. Kind kind; } MGraph; 2021/2/20 数据结构及其算法 第 7章 图 17

 • 算法 7. 1 使用邻接矩阵构造无向网 void Create. UDN(MGraph &G) { G. kind =

• 算法 7. 1 使用邻接矩阵构造无向网 void Create. UDN(MGraph &G) { G. kind = UDN; // UDN表示无向网 cin >> G. vexnum >> G. arcnum; int i, j, k; for (i=0; i<G. vexnum; ++i) cin >> G. vexs[i]; // 读入顶点数据 算法 7. 2 查找顶点 for (i=0; i<G. vexnum; ++i) int G, ++j) Vertex. Type v) { for. Locate. Vex(MGraph (j=0; j<G. vexnum; for (int i=0; i<G. vexnum; G. arcs[i][j] = INFINITY; ++i) // 例如,INFINITY=INT_MAX if (G. vexs[i] == v) return i; for (k=0; k<G. arcnum; ++k) { return -1; vi, vj; Weight. Type w; Vertex. Type } cin >> vi >> vj >> w; i = Locate. Vex(G, vi); j = Locate. Vex(G, vj); G. arcs[i][j] = G. arcs[j][i] = w; // 无向网的邻接矩阵是对称的 } } 2021/2/20 数据结构及其算法 第 7章 图 18

 • 邻接表(adjacency list)法的实现 struct Arc. Node { int adjvex; Weight. Type weight; Arc.

• 邻接表(adjacency list)法的实现 struct Arc. Node { int adjvex; Weight. Type weight; Arc. Node *nextarc; }; typedef struct { Vertex. Type data; Arc. Node *firstarc; } Vertex. Node, Adj. List[MAX_VERTEX_NUM]; typedef struct { Adj. List vertices; int vexnum, arcnum; Graph. Kind kind; } ALGraph; 2021/2/20 数据结构及其算法 第 7章 图 20

 • 算法 7. 6 使用邻接表构造无向网 void Create. UDN(ALGraph &G) { G. kind =

• 算法 7. 6 使用邻接表构造无向网 void Create. UDN(ALGraph &G) { G. kind = UDN; cin >> G. vexnum >> G. arcnum; int i, j, k; for (i=0; i<G. vexnum; ++i) { cin >> G. vertices[i]. data; G. vertices[i]. firstarc = NULL; } for (k=0; k<G. arcnum; ++k) { Vertex. Type vi, vj; Weight. Type w; cin >> vi >> vj >> w; i = Locate. Vex(G, vi); j = Locate. Vex(G. vj); Arc. Node *p = new Arc. Node; p->adjvex = j; p->weight = w; 算法 7. 7 查找顶点 p->nextarc = G. vertices[i]. firstarc; G. vertices[i]. firstarc = p; int Locate. Vex(ALGraph G, Vertex. Type v) { p = new Arc. Node; p->adjvex =++i) i; p->weight = w; for (int i=0; i<G. vexnum; p->nextarc = G. vertices[j]. firstarc; G. vertices[j]. firstarc = p; if (G. vertices[i]. data == v) return i; } return -1; } } 2021/2/20 数据结构及其算法 第 7章 图 21

 • 算法 7. 11、7. 12 深度优先遍历 bool visited[MAX_VERTEX_NUM]; void DFS(Graph G, int v)

• 算法 7. 11、7. 12 深度优先遍历 bool visited[MAX_VERTEX_NUM]; void DFS(Graph G, int v) { Visit(v); visited[v] = true; for (int w=Adj. Vex(G, v); w != -1; w=Adj. Vex(G, v, w)) { if (!visited[w]) int Adj. Vex(MGraph G, int v, int w=-1) { DFS(G, forw); (int j=w+1; j<G. vexnum; ++j) } if (G. arcs[v][j] != INFINITY) return j; } return -1; void DFSTraverse(Graph G) { } for (int v=0; v<G. vexnum; ++v) visited[v] = false; int Adj. Vex(ALGraph G, int v, int w=-1) { for (int Arc. Node v=0; v<G. vexnum; ++v) *p = G. vertices[v]. firstarc; if (!visited[v]) if (w != -1) { DFS(G, while v); (p && p->adjvex != w) p = p->nextarc; } if (p) p = p->nextarc; } return p ? p->adjvex : -1; } 2021/2/20 数据结构及其算法 第 7章 图 26

 • 递归调用过程 • 得到生成森林 DFSTraverse DFS(G, V 1) DFS(G, V 2) DFS(G, V

• 递归调用过程 • 得到生成森林 DFSTraverse DFS(G, V 1) DFS(G, V 2) DFS(G, V 4) DFS(G, V 8) DFS(G, V 9) DFS(G, V 3) DFS(G, V 7) DFS(G, V 6) DFS(G, V 5) 2021/2/20 V 9 数据结构及其算法 第 7章 图 27

 • 算法 7. 15 广度优先遍历 bool visited[MAX_VERTEX_NUM]; void BFS(Graph G, int v) {

• 算法 7. 15 广度优先遍历 bool visited[MAX_VERTEX_NUM]; void BFS(Graph G, int v) { Visit(v); visited[v] = true; Queue Q; Init. Queue(Q); En. Queue(Q, v); while (!Queue. Empty(Q)) { De. Queue(Q, v); for (int w=Adj. Vex(G, v); w != -1; w=Adj. Vex(G, v, w)) { if (!visited[w]) { Visit(w); visited[w] = true; En. Queue(Q, w); } } void BFSTraverse(Graph G) { for (int v=0; v<G. vexnum; ++v) visited[v] = false; for (int v=0; v<G. vexnum; ++v) if (!visited[v]) BFS(G, v); } 2021/2/20 数据结构及其算法 第 7章 图 29

 • 算法 7. 13 利用DFS求简单路径 bool visited[MAX_VERTEX_NUM]; bool DFS_Simple. Path. Recur(Graph G, int

• 算法 7. 13 利用DFS求简单路径 bool visited[MAX_VERTEX_NUM]; bool DFS_Simple. Path. Recur(Graph G, int vi, int vj, Stack &S) { Push(S, vi); visited[vi] = true; if (vi == vj) { Print(S); return true; } for (int w=Adj. Vex(G, vi); w != -1; w=Adj. Vex(G, vi, w)) { if (!visited[w]) { if (DFS_Simple. Path. Recur(G, w, vj, S)) return true; } } Pop(S, vi); visited[vi] = false; return false; } void思考1:对算法进行修改,求出所有的简单路径 DFS_Simple. Path(Graph G, int vi, int vj) { 思考2:利用BFS能否求简单路径?BFS求出的第一条 Stack S; Init. Stack(S); for (int v=0; v<G. vexnum; ++v) 路径有什么性质? visited[v] = false; if (DFS_Simple. Path. Recur(G, vi, vj, S)) cout << "Found a path" << endl; } 2021/2/20 数据结构及其算法 第 7章 图 33

 • U V 1 6 V 2 5 1 5 V 4 2021/2/20

• U V 1 6 V 2 5 1 5 V 4 2021/2/20 6 5 6 V 2 5 V 3 2 4 V 5 1 5 V 3 3 V 1 3 V 6 V 5 数据结构及其算法 第 7章 图 V-U V 4 5 2 4 6 V 6 37

 • Prim算法过程图示 V 1 6 V 2 1 5 V 4 4 V

• Prim算法过程图示 V 1 6 V 2 1 5 V 4 4 V 5 V 2 6 V 1 U 1 5 W 2021/2/20 6 V 2 5 2 4 V 5 6 V 4 V 6 U V 1 V 4 V 3 W V 5 U 1 5 1 4 W V 6 V 1 V 2 5 V 3 V 5 2 4 V 5 W V 4 V 3 2 U V 1 5 1 V 2 5 V 3 3 6 5 U V 1 V 6 数据结构及其算法 第 7章 图 V 2 5 V 4 V 3 3 W 1 2 4 V 5 V 6 39

 • 算法 7. 16 void Prim(MGraph G, int v 0) { // 用于存储F集合的两个数组:邻接顶点和最小边

• 算法 7. 16 void Prim(MGraph G, int v 0) { // 用于存储F集合的两个数组:邻接顶点和最小边 int adjvex[MAX_VERTEX_NUM], lowcost[MAX_VERTEX_NUM]; for (int j=0; j<G. vexnum; ++j) { if (j!=v 0) { adjvex[j] = v 0; lowcost[j] = G. arcs[v 0][j]; } } lowcost[v 0] = INFINITY; for (int i=0; i<G. vexnum-1; ++i) { // 循环n-1次 int k = Min. Edge(lowcost, G. vexnum); printf("(%d, %d): %dn", k, adjvex[k], lowcost[k]); lowcost[k] = INFINITY; for (int j=0; j<G. vexnum; ++j) { if (G. arcs[k][j] < lowcost[j]) { adjvex[j] = k; lowcost[j] = G. arcs[k][j]; } } 2021/2/20 数据结构及其算法 第 7章 图 40

 • Kruscal算法过程图示 V 1 6 V 2 5 V 4 2 4 V

• Kruscal算法过程图示 V 1 6 V 2 5 V 4 2 4 V 5 V 2 5 2 4 V 5 2021/2/20 6 V 1 6 V 2 V 6 3 4 V 5 6 V 2 V 6 数据结构及其算法 第 7章 图 V 6 6 V 1 6 2 2 4 1 5 5 V 3 V 4 5 V 3 V 5 V 4 5 1 5 3 5 1 5 V 2 V 6 6 5 V 3 3 V 5 V 4 2 4 5 1 V 4 5 V 3 V 1 6 5 1 5 3 V 6 6 V 1 6 V 2 5 V 3 3 6 5 1 V 4 V 3 3 2 4 V 5 6 V 6 42

 • 算法 7. 17 void Topological. Sort(ALGraph G) { int In. Degree[MAX_VERTEX_NUM]; Find.

• 算法 7. 17 void Topological. Sort(ALGraph G) { int In. Degree[MAX_VERTEX_NUM]; Find. In. Degree(G, In. Degree); Stack S; Init. Stack(S); void Find. In. Degree(ALGraph G, int *In. Degree) { for(inti=0; i<G. vexnum; ++i) In. Degree[i] = 0; if (!In. Degree[i]) Push(S, i); { for (int i=0; i<G. vexnum; ++i) intfor count = 0; // 统计输出顶点的个数 (Arc. Node *p=G. vertices[i]. firstarc; p; p=p->nextarc) { while. In. Degree[p->adjvex]++; (!Stack. Empty(S)) { int } i; Pop(S, i); ++count; }cout << G. vertices[i]. data << endl; } Arc. Node *p; for (p=G. vertices[i]. firstarc; p; p=p->nextarc) { k = p->adjvex; if (!(--In. Degree[k])) Push(S, k); } } if (count<G. vexnum) cout << "The graph has loop" << endl; } 2021/2/20 数据结构及其算法 第 7章 图 48