数据结构 图的部分基本算法实现

``## 数据结构 图的部分基本算法实现

   #include<stdio.h>
    #include<stdlib.h>
    #define MAXV 100
    #define INF 32767
    int visited[100] = { 0 };
    typedef struct
    {
    	int no;
    	int info;
    }VertexType;
    typedef struct
    {
    	int edges[MAXV][MAXV];
    	int n, e;
    	VertexType vexs[MAXV];
    }MGraph;           //邻接矩阵定义
    
    typedef struct ANode
    {
    	int adjvex;
    	struct ANode*nextarc;
    	int info;
    }ArcNode;    //边节点的类型
    typedef struct Vnode
    {
    	int data;
    	ArcNode*firstarc;
    }VNode;      //邻接点的头节点类型
    typedef VNode AdjList[MAXV];
    typedef struct
    {
    	AdjList adjlist;
    	int n, e;
    }AdjGraph;         //完整图邻接表类型定义
    
    void MatToList(MGraph g, AdjGraph * &G)     //邻接矩阵g转换为邻接表G
    {
    	int i, j;
    	ArcNode *p;
    	G = (AdjGraph *)malloc(sizeof(AdjGraph));
    	for (i = 0; i<g.n; i++)
    		G->adjlist[i].firstarc = NULL;
    	for (i = 0; i<g.n; i++)
    		for (j = g.n - 1; j >= 0; j--)
    			if (g.edges[i][j] != 0 && g.edges[i][j] != INF)
    			{
    				p = (ArcNode*)malloc(sizeof(ArcNode));
    				p->adjvex = j;
    				p->nextarc = G->adjlist[i].firstarc;
    				G->adjlist[i]. firstarc = p;
    			}
    	G->n = g.n;
    	G->e = g.e;
    }
    void DisplistAdj(AdjGraph*&G)       //输出邻接表
    {
    	int i;
    	ArcNode*p;
    	for (i = 0; i<G->n; i++)
    	{
    		p = G->adjlist[i].firstarc;
    		printf("%3d: ", i);
    		while (p != NULL)
    		{
    			printf("%3d->", p->adjvex);
    			p = p->nextarc;
    		}
    		printf("/\n");
    	}
    	printf("\n");
    }
    void DispMat(MGraph g)            //输出邻接矩阵
    {
    	int i, j;
    	for (i = 0; i<g.n; i++)
    	{
    		for (j = 0; j<g.e; j++)
    			printf("%3d",g.edges[i][j]);
    				printf("\n");
    	}
    	printf("\n");
    }
    void DFS(AdjGraph * G, int v)                //深度优先遍历
    {
    	ArcNode*p;
    	visited[v] = 1;
    	printf("%3d", v);
    	p = G->adjlist[v].firstarc;
    	while (p != NULL)
    	{
    		if (visited[p->adjvex] == 0)
    			DFS(G, p->adjvex);
    		p = p->nextarc;
    	}
    }
    void BFS(AdjGraph * G, int v)        //广度优先遍历
    {
    	ArcNode*p;
    	int queue[MAXV], front = 0, rear = 0;
    	int visited[MAXV];
    	int w, i;
    	for (i = 0; i < G->n; i++)
    		visited[i] = 0;
    	printf("%3d", v);
    	visited[v] = 1;
    	rear = (rear + 1) % MAXV;
    	queue[rear] = v;
    	while (front != rear)
    	{
    		front = (front + 1) % MAXV;
    		w = queue[front];
    		p = G->adjlist[w].firstarc;
    		while (p != NULL)
    		{
    			if (visited[p->adjvex] == 0)
    			{
    				printf("%3d", p->adjvex);
    				visited[p->adjvex] = 1;
    				rear = (rear + 1) % MAXV;
    				queue[rear] = p->adjvex;
    			}
    			p = p->nextarc;
    		}
    	}
    	printf("\n\n");
    }                                                    
    void ExistPath(AdjGraph*G, int u, int v, bool &has)     //判断路径存在
    {                                                       //has表示u到v是否有路径,初值为false
    	int w;
    	ArcNode*p;
    	visited[u] = 1;
    	if (u == v)
    	{
    		has = true;
    		return;
    	}
    	p = G->adjlist[u].firstarc;
    	while (p != NULL)
    	{
    		w = p->adjvex;
    		if (visited[w] == 0)
    			ExistPath(G, w, v, has);
    		p = p->nextarc;
    	}
    }
    void FindaPath(AdjGraph*G, int u, int v, int path[], int d)   //输出图G中从顶点u到v的一条简单路径
    {                                                             //路径长度d
    	int w, i;
    	ArcNode*p;
    	visited[u] = 1;
    	d++;
    	path[d] = u;
    	if (u == v)
    	{
    		for (i = 0; i <= d; i++)
    			printf("%3d", path[i]);
    		printf("\n");
    		return;
    	}
    	p = G->adjlist[u].firstarc;
    	while (p != NULL)
    	{
    		w = p->adjvex;
    		if (visited[w] == 0)
    			FindaPath(G, w, v, path, d);
    		p = p->nextarc;
    	}
    }
    void FindPath(AdjGraph*G, int u, int v, int path[], int d)   //查找并输出从顶点u到v的所有简单路径
    {
    	int w, i;
    	ArcNode*p;
    	d++;
    	path[d] = u;
    	visited[u] = 1;
    	if (u == v && d >= 1)
    	{
    		printf("  2");
    		for (i = 1; i <= d; i++)
    			printf("%3d", path[i]);
    		printf("\n");
    	}
    	p = G->adjlist[u].firstarc;
    	while (p != NULL)
    	{
    		w = p->adjvex;
    		if (visited[w] == 0)
    			FindPath(G, w, v, path, d);
    		p = p->nextarc;
    	}
    	visited[u] = 0;
    }
    void PathAll(AdjGraph*G, int u, int v,int l, int path[], int d)   //输出从顶点u到v的长度为l的所有简单路径
    {
    	int w, i;
    	ArcNode*p;
    	d++;
    	path[d] = u;
    	visited[u] = 1;
    	if (u == v && d == l)
    	{
    		for (i = 0; i <= d; i++)
    			printf("%3d", path[i]);
    		printf("\n");
    	}
    	p = G->adjlist[u].firstarc;
    	while (p != NULL)
    	{
    		w = p->adjvex;
    		if (visited[w] == 0)
    			PathAll(G, w, v, l, path, d);
    		p = p->nextarc;
    	}
    	visited[u] = 0;
    }
    
    int main()
    {
    	int i, j;
    	MGraph g;
    	AdjGraph*G;
    	g.n = 5, g.e = 5;
    	int A[MAXV][MAXV] = {
    		{ 0,1,0,1,1 },{ 1,0,1,1,0 },{ 0,1,0,1,1 },{ 1,1,1,0,1 },{ 1,0,1,1,0 } };
    	for (i = 0; i < g.n; i++)
    		for (j = 0; j < g.e; j++)
    			g.edges[i][j] = A[i][j];
    	printf("邻接矩阵g:\n");
    	DispMat(g);
    	MatToList(g, G);
    	printf("邻接矩阵转化为邻接表G:\n");
    	DisplistAdj(G);
    	printf("从顶点2出发的深度优先访问序列是:\n");
    	DFS(G, 2);
    	printf("\n\n");
    	printf("从顶点2出发的广度优先遍历序列是:\n");
    	BFS(G, 2);
    	printf("顶点2-4是否存在简单路径:\n");
    	for (i = 0; i < G->n; i++)
    		visited[i] = 0;
    	bool has = 0;
    	ExistPath(G, 4, 4, has);
    	if (has == 1)
    		printf("  存在\n");
    	else
    		printf("  不存在\n");
    	printf("\n");
    	int path[MAXV] = { 0 };
    	printf("从顶点2到4的一条简单路径为:\n");
    	for (i = 0; i < G->n; i++)
    		visited[i] = 0;
    	FindaPath(G, 2, 4, path, -1);
    	printf("\n");
    	printf("从顶点2到4的所有简单路径为:\n");
    	for (i = 0; i < G->n; i++)
    		visited[i] = 0;
    	FindPath(G, 2, 4, path, -1);
    	printf("\n");
    	printf("从顶点1到4的长度为3的所有简单路径为:\n");
    	for (i = 0; i < G->n; i++)
    		visited[i] = 0;
    	PathAll(G, 1, 4, 3, path, -1);
    	printf("\n");
    }
  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值