邻接表的实现
今天想練習一下圖算法,有些圖算法的基礎數據結構是鄰接表,于是想著用C實現一下,雖說wiki上有一個鄰接表的實現,但是自己還是想練一下手,在網上也搜到了別人的鄰接表實現,發現大同小
異,然后就在別人的基礎上修改了一下得到了這個版本,記錄一下,供以后練習使用。
1.鄰接表概念
一張圖,如果不考慮空間占用問題的話,用鄰接矩陣存儲是最方便的了,但有時候,圖很稀疏,用矩陣存儲就不劃算了,這時候可以考慮用鄰接表來實現,另外,有些算法用鄰接表比較合適。
鄰接表的圖示如下(網絡來源):
關于鄰接表的概念,要清晰易懂的話上面的鏈接就很好,要詳盡的話看wiki就好了,我的代碼是在下面這個網頁的基礎上修改的。
?
2.鄰接表需注意的點
- 一般需要一個頂點數組來保存頂點信息
- 每個頂點數組后面跟著一個單鏈表,表示與該頂點直接相連的頂點
- 頂點數組中保存有一個指向單鏈表頭部的指針,以及頂點信息的相應描述
?
3.鄰接表的實現
頭文件:
| /* by areslipan@163.com filename: adjlist.h */ #ifndef _ADJLIST_ #define _ADJLIST_ #include<iostream> using namespace std; #define MAXVEX 100 /* 最大頂點數,應由用戶定義 */ typedef int VertexType; /* 頂點類型應由用戶定義 */ typedef int EdgeType; /* 邊上的權值類型應由用戶定義 */ typedef struct EdgeNode/* 邊表結點 */ { int adjvex;/* 鄰接點域,存儲該頂點對應的下標 */ EdgeType weight;/* 用于存儲權值,對于非網圖可以不需要 */ struct EdgeNode *next; /* 鏈域,指向下一個鄰接點 */ } EdgeNode; typedef struct VextexNode/* 頂點表結點 */ { VertexType data;/* 頂點域,存儲頂點信息 */ EdgeNode *firstedge;/* 邊表頭指針 */ } VextexNode, AdjList[MAXVEX]; typedef struct { AdjList adjList; int numNodes, numEdges; /* 圖中當前頂點數和邊數 */ } GraphAdjList; void create_adjlist_graph(GraphAdjList *Gp); void show_adjlist_graph(GraphAdjList *Gp); void destroy_adjlist_graph(GraphAdjList *Gp); #endif |
實現文件:
| /* by areslipan@163.com filename : adjlist.cpp */ #include "adjlist.h" void create_adjlist_graph(GraphAdjList *Gp) { int i, j, k,w; EdgeNode *pe; cout << "輸入頂點數和邊數(空格分隔):" << endl; cin >> Gp->numNodes >> Gp->numEdges; cout << "輸入頂點信息:" << endl; for (i = 0 ; i < Gp->numNodes; i++) { cin >> Gp->adjList[i].data; Gp->adjList[i].firstedge = NULL;/* 將邊表置為空表 */ } for (k = 0; k < Gp->numEdges; k++)/* 建立邊表 */ { cout << "輸入邊(vi,vj,w)的頂點序號i,j(空格分隔):" << endl; cin >> i >> j >> w; pe = (EdgeNode *)malloc(sizeof(EdgeNode)); pe->adjvex = j;/* 鄰接序號為j */ pe->weight = w; /* 將pe的指針指向當前頂點上指向的結點 */ pe->next = Gp->adjList[i].firstedge; Gp->adjList[i].firstedge = pe;/* 將當前頂點的指針指向pe */ //如果是無向圖可以加上下面這段代碼 /* pe = (EdgeNode *)malloc(sizeof(EdgeNode)); pe->adjvex = i; pe->next = Gp->adjList[j].firstedge; Gp->adjList[j].firstedge = pe;*/ } cout<<"有向圖的鄰接表創建成功..."<<endl; } void show_adjlist_graph(GraphAdjList *Gp) { cout<<"鄰接表如下:"<<endl; if(Gp->numNodes == 0 || Gp->numEdges == 0)cout<<"The adjlist is empty!"<<endl; for(int v=0;v<Gp->numNodes;++v) { cout<<"V"<<v<<":"; if(Gp->adjList[v].firstedge==NULL)cout<<"NULL"<<endl; else { EdgeNode *cur=Gp->adjList[v].firstedge; while(cur!=NULL) { cout<<"V"<<cur->adjvex<<"("<<cur->weight<<")"<<" "; cur=cur->next; } cout<<endl; } } } void destroy_adjlist_graph(GraphAdjList *Gp) { if(Gp->numNodes == 0 || Gp->numEdges == 0)return ; else { for(int v=0;v<Gp->numNodes;++v) { while(Gp->adjList[v].firstedge!=NULL) { EdgeNode *cur=Gp->adjList[v].firstedge; Gp->adjList[v].firstedge=cur->next; free(cur); } } } cout<<"鄰接表銷毀成功..."<<endl; } |
測試文件:
| /* by areslipan@163.com filename : test.cpp */ #include "adjlist.h" using namespace std; int main() { GraphAdjList g; create_adjlist_graph(&g); show_adjlist_graph(&g); destroy_adjlist_graph(&g); show_adjlist_graph(&g); system("pause"); } |
轉載于:https://www.cnblogs.com/obama/p/3347459.html
總結
- 上一篇: 小米9拍照能超过p20pro吗(小米官方
- 下一篇: DOM节点中属性nodeName、nod