(数据结构)1.实现图的邻接矩阵和邻接表的存储 2.实现图的遍历算法

实验内容

1、编写一个程序graph.cpp,设计带权图的邻接矩阵与邻接表的创建和输出运算,并在此基础上设计一个主程序exp8-1.cpp完成以下功能。
(1)建立如图8.54所示的有向图G的邻接矩阵,并输出之。
(2)建立如图8.54所示的有向图G的邻接表,并输出之。
(3)销毁图G的邻接表。
2、编写一个程序travsal.cpp实现图的两种遍历运算,并在此基础上设计一个程序exp8-2.cpp完成以下功能。
(1)输出如图8.54的有向图G从顶点0开始的深度优先遍历序列(递归算法)。
(2)输出如图8.54的有向图G从顶点0开始的深度优先遍历序列(非递归算法)。
(3)输出如图8.54的有向图G从顶点0开始的广度优先遍历序列。

代码实现

1、

#include <iostream>
#include <malloc.h>
#define INF 32767	//定义无穷大 
#define MAXV 100	//最大顶点个数
typedef char InfoType;
 
//定义邻接矩阵类型 
typedef struct
{
	int no;
	InfoType info;
}VertexType;
typedef struct
{
	int edges[MAXV][MAXV];
	int n,e;
	VertexType vexs[MAXV]; 
}MatGraph;

//定义邻接表类型
typedef struct ANode
{
	int adjvex;
	struct ANode *nextarc;
	int weight;
 } ArcNode;
typedef struct Vnode
{
	InfoType info;
	int count;
	ArcNode *firstarc;
}VNode;
typedef struct
{
	VNode adjlist[MAXV];
	int n,e;
}AdjGraph;

//邻接矩阵的基本运算:
//创建邻接矩阵 
void CreateMat(MatGraph &g,int A[MAXV][MAXV],int n,int e)
{
	int i,j; 
	g.n=n;g.e=e;
	for(i=0;i<g.n;i++)
		for(j=0;j<g.n;j++)
			g.edges[i][j]=A[i][j];
}
//输出邻接矩阵
void DispMat(MatGraph g)
{
	int i,j;
	for(i=0;i<g.n;i++)
	{
		for(j=0;j<g.n;j++)
		{
			if(g.edges[i][j]!=INF)
				printf("%4d",g.edges[i][j]);
			else
				printf("%4s","-");
		}
		printf("\n");
	}
 } 
 
 //邻接表的基本运算:
 //创建邻接表 
 void CreateAdj(AdjGraph *&G,int A[MAXV][MAXV],int n,int e) 
 {
 	int i,j;
	ArcNode *p;
	G=(AdjGraph *)malloc(sizeof(AdjGraph));
	for(i=0;i<n;i++)
		G->adjlist[i].firstarc=NULL;
	for(i=0;i<n;i++)
	{
		for(j=n-1;j>=0;j--)
		{
			if(A[i][j]!=0&&A[i][j]!=INF)
			{
				p=(ArcNode *)malloc(sizeof(ArcNode));
				p->adjvex=j;
				p->weight=A[i][j];
				p->nextarc=G->adjlist[i].firstarc;
				G->adjlist[i].firstarc=p;
			}
		}
	}
	G->n=n;G->e=n;
 } 
 //输出邻接表
 void DispAdj(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[%d]->",p->adjvex,p->weight);
 			p=p->nextarc ;
		 }
		printf("^\n");
	 }
  } 
//销毁邻接表
void DestroyAdj(AdjGraph *&G)
{
	int i;
	ArcNode *pre,*p;
	for(i=0;i<G->n;i++)
	{
		pre=G->adjlist[i].firstarc;
		if(pre!=NULL)
		{
			p=pre->nextarc ;
			while(p!=NULL)
			{
				free(pre);
				pre=p;p=p->nextarc ;
			}
			free(pre);
		}
	 } 
	 free(G);
 } 
int main()
{
	MatGraph g;
	AdjGraph *G;
	int A[MAXV][MAXV]={{0,1,0,1,0,0},
						{0,0,1,0,0,0},
						{1,0,0,0,0,1},
						{0,0,1,0,0,1},
						{0,0,0,1,0,0},
						{1,0,0,0,1,0}};
	int n=6,e=10;
	CreateMat(g,A,n,e);
	printf("图G的邻接矩阵:\n");
	DispMat(g);
	CreateAdj(G,A,n,e);
	printf("图G的邻接表:\n");
	DispAdj(G);
	DestroyAdj(G);
	return 1; 
} 

结果截图:
在这里插入图片描述
2、

#include<stdio.h>
#include<malloc.h>
#define MAXV 100
//以下定义邻接矩阵类型
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;
}ALGraph;
int visited[MAXV];

//递归深度优先遍历
void DFS(ALGraph *G,int v)   
{
 ArcNode *p;
 visited[v]=1;
 printf("%3d",v);
 p=G->adjlist[v].firstarc;
 while(p)
 {
  if(visited[p->adjvex]==0)
     DFS(G,p->adjvex);
        p=p->nextarc;
 }
}
//非递归深度优先遍历
void DFS1(ALGraph *G,int v)
{
 ArcNode *p;
 ArcNode *St[MAXV];
 int top=-1,i,w;
 for(i=0;i<G->n;i++)
   visited[i]=0;
    printf("%3d",v);
    visited[v]=1;
    top++;
    St[top]=G->adjlist[v].firstarc;
    while(top>-1)
    {
     p=St[top];top--;
     while(p)
     {
      w=p->adjvex;
      if(visited[w]==0)
      {
       printf("%3d",w);
       visited[w]=1;
       top++;
       St[top]=G->adjlist[w].firstarc;
       break;
      }
      p=p->nextarc;
     }
    }
    printf("\n");
}

//广度优先遍历 
void BFS(ALGraph *G,int v)
{
 ArcNode *p;
 int queue[MAXV],front=0,rear=0;
 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)
     {
      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");
}
void DispAdj(ALGraph *G)       //输出邻接表
{
 int i;
 ArcNode *p;
 for(i=0;i<G->n;i++)
 {
  p=G->adjlist[i].firstarc;
  if(p)  printf("%3d:",i);
  while(p)
  {
   printf("%3d->",p->adjvex);
   p=p->nextarc;
  }
  printf("\n");
 }
}
void MatToList(MGraph g,ALGraph *&G)        //将邻接矩阵 g 转换为邻接表 G
{
 int i,j,n=g.n;
 ArcNode *p;
 G=(ALGraph *)malloc(sizeof(ALGraph));
 for(i=0;i<n;i++)
   G->adjlist[i].firstarc=NULL;
    for(i=0;i<n;i++)
      for(j=n-1;j>=0;j--)
        if(g.edges[i][j])
        {
         p=(ArcNode *)malloc(sizeof(ArcNode));
         p->adjvex=j;
         p->info=g.edges[i][j];
         p->nextarc=G->adjlist[i].firstarc;
         G->adjlist[i].firstarc=p;
        }
    G->n=n;
    G->e=g.e;
}
 
int main()
{
 int i,j;
 MGraph g;
 ALGraph *G;
 int A[MAXV][6]={
  {0,5,0,7,0,0},
  {0,0,4,0,0,0},
  {8,0,0,0,0,9},
  {0,0,5,0,0,6},
  {0,0,0,5,0,0},
  {3,0,0,0,1,0}
 };
 g.n=6;g.e=10;
 for(i=0;i<g.n;i++)
 for(j=0;j<g.n;j++)
     g.edges[i][j]=A[i][j];
    G=(ALGraph *)malloc(sizeof(ALGraph));
    MatToList(g,G);
    printf("从顶点0开始的DFS(递归算法):\n");
    DFS(G,0);  printf("\n");
    printf("从顶点0开始的DFS(非递归算法):\n");
    DFS1(G,0);  printf("\n");
    printf("从顶点0开始的BFS(递归算法):\n");
    BFS(G,0);  printf("\n");
}      

结果截图:
在这里插入图片描述

  • 67
    点赞
  • 391
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
好的,我很乐意回答你的问题。首先,让我们来了解一下有向图邻接矩阵邻接表存储结构。 有向图邻接矩阵存储结构是用一个二维数组来表示中各个顶点之间的关系。其中,数组的行和列坐标对应于中的各个顶点,数组元素的值表示两个顶点之间是否存在一条有向边,也可以表示边的权值。如果顶点 i 和顶点 j 之间存在一条边,则数组元素 a[i][j] 的值为 1 或非零值;如果不存在一条边,则 a[i][j] 的值为 0。 有向图邻接表存储结构是利用链表来存储中各个顶点之间的关系。具体来说,每个顶点对应一个链表,链表中存储顶点所指向的顶点列表。这个过程可以用一个数组和多个链表来实现,其中数组中的每个元素都对应一个链表。 接下来,让我们来实现两种遍历运算和简单路径求解: 1. 深度优先遍历(DFS):从起点出发,尽可能深地探索每一个分支,直到该路径不能继续为止。然后回溯到前一个节点,继续探索其他分支。 2. 广度优先遍历(BFS):从起点出发,按照距离由近及远的顺序依次访问每个顶点,直到遍历完所有的顶点为止。 3. 简单路径求解:在有向图中,简单路径是指不包含重复边和重复顶点的路径。简单路径求解算法可以使用深度优先遍历或广度优先遍历实现。 以上就是有关有向图邻接矩阵邻接表存储结构以及遍历运算和简单路径求解的一些基本知识和算法。希望这能对你有所帮助!

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值