【圖(上)】小白專場:如何建立圖
阿新 • • 發佈:2018-11-22
1、用鄰接矩陣表示圖
typedef struct GNode *PtrToGNode;
struct GNode
{
int Nv; //頂點數
int Ne; //邊數
DataType Data[MaxVertexNum]; //存頂點的資料
};
typedef PtrToGNode MGraph; //以鄰接矩陣儲存的圖型別
MGraph初始化
- 初始化一個有VertexNum個頂點但沒有邊的圖
typedef int Vertex; //用頂點下標表示頂點,為整型
MGraph CreateGraph(int VertexNum)
{
Vertex V, W;
MGraph Graph;
Graph = (MGraph)malloc(sizeof(struct GNode));
Graph->Nv = VertexNum;
Graph->Ne = 0;
/* 注意:這裡預設頂點編號從0開始,到(Graph->Nv - 1) */
for (V = 0; V<Graph->Nv; V++)
for (W = 0; W<Graph->Nv; W++)
Graph->G[V][W] = 0; //或INFINITY
return Graph;
}
向MGraph中插入邊
typedef struct ENode *PtrToENode;
struct ENode
{
Vertex V1, V2; //有向邊<V1, V2>
WeightType Weight; //權重
};
typedef PtrToENode Edge;
void InsertEdge(MGraph Graph, Edge E)
{
Graph->G[E->V1][E->V2] = E->Weight;//插入邊<V1, V2>
Graph->G[E->V2][E->V1] = E->Weight;//若是無向圖,還要插入邊<V2, V1>
}
完整地建立一個MGraph
- 輸入格式
Nv Ne
V1 V2 Weight
……
MGraph BuildGraph()
{
MGraph Graph;
Edge E;
Vertex V;
int Nv, i;
scanf("%d", &Nv);
Graph = CreateGraph(Nv);
scanf("%d", &(Graph->Ne));
if (Graph->Ne != 0)
{
E = (Edge)malloc(sizeof(struct ENode));
for (i = 0; i<Graph->Ne; i++)
{
scanf("%d %d %d",&E->V1, &E->V2, &E->Weight);
InsertEdge(Graph, E);
}
}
//如果頂點有資料的話,讀入資料
for (V = 0; V<Graph->Nv; V++)
scanf(" %c", &(Graph->Data[V]));
return Graph;
}
簡單方法實現用鄰接矩陣表示圖的建立
int G[MAXN][MAXN], Nv, Ne;
void BuildGraph()
{
int i, j, v1, v2, w;
scanf("%d", &Nv);
//CreateGraph
for (i = 0; i<Nv; i++)
for (j = 0; j<Nv; j++)
G[i][j] = 0; //或INFINITY
scanf("%d", &Ne);
for (i = 0; i<Ne; i++)
{
scanf("%d %d %d", &v1, &v2, &w);
//InsertEdge
G[v1][v2] = w;
G[v2][v1] = w;
}
}
此種方法的缺點,這種建立方法只適用於用鄰接矩陣表示圖,若換一種表示方法,就不適用了,不推薦
2、用鄰接表表示圖
- 鄰接表:G[N]為指標陣列,對應矩陣每行一個連結串列,只存非0元素
typedef struct Vnode
{
PtrToAdjVNode FirstEdge;
DataType Data; //存頂點的資料
} AdjList[MaxVertexNum];
//AdjList是鄰接表型別,
//有幾個頂點就有幾個連結串列,每一個連結串列開始於一個結點和一個指標
typedef struct GNode *PtrToGNode;
struct GNode
{
int Nv; //頂點數
int Ne; //邊數
AdjList G; //鄰接表
};
typedef PtrToGNode LGraph;
//以鄰接表方式儲存的圖型別,包括有頂點,邊和鄰接表
typedef struct AdjVNode *PtrToAdjVNode;
struct AdjVNode {
Vertex AdjV; //鄰接點下標
WeightType Weight; //邊權重
PtrToAdjVNode Next;
};
LGraph初始化
- 初始化一個有VertexNum個頂點但沒有邊的圖
typedef int Vertex; //用頂點下標表示頂點,為整型
LGraph CreateGraph(int VertexNum)
{
Vertex V, W;
LGraph Graph;
Graph = (LGraph)malloc(sizeof(struct GNode));
Graph->Nv = VertexNum;
Graph->Ne = 0;
//注意:這裡預設頂點編號從0開始,到(Graph->Nv - 1)
for (V = 0; V<Graph->Nv; V++)
Graph->G[V].FirstEdge = NULL;
return Graph;
}
向LGraph中插入邊
void InsertEdge(LGraph Graph, Edge E)
{
PtrToAdjVNode NewNode;
/************* 插入邊<V1, V2> ************/
//為V2建立新的鄰接點
NewNode = (PtrToAdjVNode)malloc(sizeof(struct AdjVNode));
NewNode->AdjV = E->V2;
NewNode->Weight = E->Weight;
//將V2插入V1的表頭
NewNode->Next = Graph->G[E->V1].FirstEdge;
Graph->G[E->V1].FirstEdge = NewNode;
/****** 若是無向圖,還要插入邊<V2, V1> ******/
//為V1建立新的鄰接點
NewNode = (PtrToAdjVNode)malloc(sizeof(struct AdjVNode));
NewNode->AdjV = E->V1;
NewNode->Weight = E->Weight;
//將V1插入V2的表頭
NewNode->Next = Graph->G[E->V2].FirstEdge;
Graph->G[E->V2].FirstEdge = NewNode;
}
完整地建立一個LGraph
同完整地建立一個MGraph相同