Operation set of adjacency matrix graph

Operation set of adjacency matrix graph

Graph creation

#include <stdio.h>
#include <stdlib.h>
#define weighttype int
#define maxvertexnum 100
typedef int vertex;

//邻接矩阵操作
//图
struct Mgnode {
    
    
	int Nv,Ne;
	weighttype G[maxvertexnum][maxvertexnum];
};
typedef struct Mgnode *Mgraph;
//边
struct edgenode {
    
    
	vertex v1, v2;
	weighttype weight;
};
typedef struct edgenode *edge;
//边的插入
void insertedge(Mgraph gr, edge e) {
    
    
	gr->G[e->v1][e->v2] = e->weight;
	gr->G[e->v2][e->v1] = e->weight;
}
//建立空图
Mgraph createMgraph(int vertexnum) {
    
    
	vertex v, w;
	Mgraph graph;
	graph = (Mgraph)malloc(sizeof(struct Mgnode));
	graph->Nv = vertexnum;
	graph->Ne = 0;
	for (v = 0; v < graph->Ne; v++)
		for (w = 0; w < graph->Ne; w++)
			graph->G[v][w] = 0;
	return graph;
}
//建立图
Mgraph buildMgraph() {
    
    
	Mgraph g;
	edge e;
	int vertexnum;
	scanf("%d", &vertexnum);
	g = createMgraph(vertexnum);
	scanf("%d", &g->Ne);
	if (g->Ne > 0){
    
    
	e = (edge)malloc(sizeof(struct edgenode));
	for (int i = 0; i < g->Ne; i++) {
    
    
		scanf("%d %d %d", &e->v1, &e->v2, &e->weight);
		insertedge(g, e);
	}
	}
	return g;
}

Breadth first traversal of BFS

//广度优先遍历 BFS
#define infinity 100000000
int isedge(Mgraph g, vertex v1, vertex v2) {
    
    
	return g->G[v1][v2] < infinity ? true : false;
}
void visit(vertex w) {
    
    
	printf("%d", w);
}
void BFS(Mgraph g, vertex s) {
    
     //从s开始遍历
	quene q = createquene(maxisize);
	vertex v, w;
	visit(s);
	visited[s] = true;
	enquene(q, s);
	while (!isempty(q)) {
    
    
		v = dequene(q);
		for (w = 0; w < g->Nv; w++)  //与邻接表不同,不知道v的邻接点是哪些,需要对所有顶点进行一个判别
			if (isedge(g, v, w) && !visited) {
    
    
				visit(w);
				visited[w] = true;
				enquene(q, w);
			}
	}
}

dijkstra algorithm

//dijkstra算法
#define infinity 1000000
int findmindist(Mgraph g,int dist[],int collected[]) {
    
    
	/*返回未被收录顶点中dist最小者 */
	vertex minv, v;
	int MinDist = infinity;
	for (v = 0; v<g->Nv;v++) {
    
    
		if (collected[V] == false && dist[v]<MinDist) {
    
    
			/* 若V未被收录,且dist[V]更小 */
			MinDist = dist[v]; /* 更新最小距离 */
			minv = v; /* 更新对应顶点 */
		}
	}
	if (MinDist < infinity) /* 若找到最小dist */
		return minv; /* 返回对应的顶点下标 */
	else return false;  /* 若这样的顶点不存在,返回错误标记 */
}

int dijkstra(Mgraph g, int dist[], int path[], vertex s) {
    
    
	int collected[maxvertexnum];
	for (int v = 0; v < g->Nv; v++) {
    
    
		collected[v] = false;
		dist[v] = g->G[s][v];
		if (dist[v] < infinity) path[v] = s;
		else path[v] = -1;
	}
	dist[s] = 0;
	collected[s] = true;
	path[s] = -1;      //s收入
	while (1) {
    
    
		vertex v = findmindist(g);
		if (v == false) break;
		collected[v] = true;      //每次收录dist最小的点
		for (vertex w = 0; w < g->Nv; w++) 
			if (!collected[w] && dist[v] + g->G[v][w] < dist[w]) {
    
    
				dist[w] = dist[v] + g->G[v][w];
				path[w] = v;
			}	   //更新邻接点的dist
	}
}

Floyd algorithm

int floyd(Mgraph g, weighttype D[][maxvertexnum], vertex path[][maxvertexnum]) {
    
    
	vertex i, j, k;
	for (i = 0; i < g->Nv; i++)
		for (j = 0; j < g->Nv; j++) {
    
    
			D[i][j] = g->G[i][j];
			path[i][j] = -1;
		}
	for (k = 0; k < g->Nv; k++)
		for (i = 0; i < g->Nv; i++)
			for (j = 0; j < g->Nv; j++) {
    
    
				if (D[i][j] > D[i][k] + D[k][j]) {
    
    
					D[i][j] = D[i][k] + D[k][j];
					path[i][j] = k;      //递归打印i到j的路径,ij-k;ik-m;im-n;
				}
			}
	return true;
}

prime algorithm

//prime算法

int findmindist1(Mgraph g, int dist[]) {
    
    
	/*返回未被收录顶点中dist最小者 */
	vertex minv, v;
	int MinDist = infinity;
	for (v = 0; v < g->Nv; v++) {
    
    
		if (dist[v] != 0 && dist[v] < MinDist) {
    
    
			/* 若V未被收录,且dist[V]更小 */
			MinDist = dist[v]; /* 更新最小距离 */
			minv = v; /* 更新对应顶点 */
		}
	}
	if (MinDist < infinity) /* 若找到最小dist */
		return minv; /* 返回对应的顶点下标 */
	else return false;  /* 若这样的顶点不存在,返回错误标记 */
}

int prime(Mgraph g, Lgraph MST) {
    
    
	vertex parent[maxvertexnum], v, w;
	weighttype dist[maxvertexnum], totalweight;
	for (int i = 0; i < g->Nv; i++){
    
         //默认初始点是0
		dist[i] = g->G[0][i];
		parent[i] = 0;
	}                                      //初始化dist与parent数组

	int totalweight, vcount;
	totalweight = 0;
	vcount = 0;
	MST = createLgraph(g->Nv);

	dist[0] = 0;
	parent[0] = -1;
	vcount++;     //将0收入

	edge  e = (edge)malloc(sizeof(struct edgenode));
	while (1) {
    
    
		v = findmindist1(g, dist);    //取最小的distv
		if (v == false) break;
		
		e->v1 = parent[v];    //将dist最小的顶点收入最小生成树
		e->v2 = v;
		insertedge(MST, e);
		totalweight += dist[v];
		dist[v] = 0;
		vcount++;

		for (w = 0; w < g->Nv; w++)        
			if (dist[w] != 0 && g->G[v][w] < infinity)   //对于v的每个邻接点
				if (g->G[v][w] < dist[w]) {
    
                   //边权重小于dist,则更新dist
					dist[w] = g->G[v][w];
					parent[w] = v;
				}                                          //更新后循环调用
	}
	if (vcount < g->Nv) totalweight = false;   //判断图是否联通
	return false;
}

Guess you like

Origin blog.csdn.net/qq_40602655/article/details/107548606