算法基础(十):--有向图的邻接表创建

来源:互联网 发布:xp怎么网络共享打印机 编辑:程序博客网 时间:2024/05/17 06:29

邻接表=邻接链表。

我觉得,还是要自己写写,写出来,理解才会更深一点,以前眼高手低,不知其中厉害啊。

其实还是蛮有趣的!我觉得,还是要把数据结构学好,工具总是在变,但是思想才是最重要的。

代码的注释应该还是非常详细的,学这个,还是要结合书上的图,就是严蔚敏版数据结构。

代码如下:

PS:遍历我就没写了,深度优先,广度优先,前面都写过了,偷懒了!

#include"stdafx.h"#include"Basic_Symbol.h"#include"ZJC_Queue.h"//数据结构学习记录..ZJC//vex:顶点,arc:边//还是自己动手好啊,写多了理解就会加深啊!#define MAX_VERTEX_NUM 20//单条链表的最大数量typedef int InfoType;typedef int VertexType ;//最低级typedef struct ArcNode//链表中的元素数据结构,即表节点{int adjvex;//该弧所指向的顶点位置struct ArcNode *next;//指向下一条弧的指针InfoType *info;//该数据域存储和边或者弧相关的信息,如权值等其他信息。}ArcNode;//二级控制typedef struct VNode{VertexType data;//存储顶点的名或其他信息的数据域ArcNode*firstarc;//指向链表中的第一个节点}VNode,AdjList[MAX_VERTEX_NUM];//一级控制typedef struct{AdjListvertices;int vexnum,arcnum;//这个图中的顶点数量,边数量int kind;//图的种类标志}ALGraph;//相关定义完毕!下面是函数实现//下面是:有向图的邻接链表存储方式构建Status CreatALGraph(ALGraph *G){int ListNum = 0;//保证表从0开始,然后依次累加,这样不会离散..int vex,arc;int tempVex;int tempVexNum;//临时数,存储总的指向的节点数量ArcNode* node = NULL;ArcNode* tempPoint = NULL;printf("请输入要建立的图的顶点数,边数:\n");scanf("%d %d",&vex,&arc);//3,3G->vexnum = vex;//3G->arcnum = arc;//3//开始构建顶点关系,依次询问每个顶点指向了其他的哪些顶点,循环次数为总的顶点数,只关心箭头从谁发出//初始化:for(int i = 0;i<MAX_VERTEX_NUM;i++)G->vertices[i].data = -1;for(int i = 0;i<vex;i++){printf("请问%d号节点指向了多少个节点?请输入:\n",i+1);scanf("%d",&tempVexNum);if(tempVexNum > 0)//存在指向,才执行下面,如果是无向图,那么就不存在这个,因为没有孤岛{//printf("\nlistNum = %d",ListNum);G->vertices[ListNum].data = i;//这个data用来存储头结点的号数if(ListNum >= MAX_VERTEX_NUM ){printf("满了");return 0;}for(int j = 0;j<tempVexNum;j++)//每输入就挂在链表上{printf("\n请分别所指向的节点%d的编号:\n",j+1);scanf("%d",&tempVex); node = (ArcNode*)malloc(sizeof(ArcNode));//创建链表节点,node->next = NULL;node->adjvex = tempVex;// 先暂时写着吧,也就是说我现在把这个理解成了被指向的顶点的编号if(j == 0)//表示是第一个,才头结点连接,否则用表节点连接{G->vertices[i].firstarc = node;//连接成功}else {//printf("\n检测上一个的指针是否正确:%d",tempPoint->adjvex);tempPoint->next = node;//连接在上一个的末尾}//printf("节点创建成功!其号数:%d",node->adjvex);tempPoint = node;//tempPoint是上一个节点的地址。}printf("\nA节点%d的链表建立完成!!!开始下一个节点的链表建立\n",i);}else {G->vertices[ListNum].data = -1;G->vertices[i].firstarc = NULL;}ListNum++;//创建,全局静态,刚刚的问题就是如果输入的vex = 0.那么就不会记录进去..无论是否为0,都应该被记录//OK,这样就知道了节点i所指向的其他全部节点的编号了}printf("\n邻接表建立完成!");return 1;}void ShowGraph(ALGraph G)//验证邻接表的创建是否正确,主要是验证其中的数据..{//printf("\n检测数据..G.arcnum = %d,G.vexnum = %d,G[0].data = %d",G.arcnum,G.vexnum,G.vertices[0].data);ArcNode* temp;for(int i = 0;i<G.arcnum ;i++)//对每一条链表进行验证,检测次数为所有边的条数{printf("\n输出链表%d号中的所有数据如下:",i + 1);if(G.vertices[i].data != -1)//表明有数据{//输出该条链表中的所有数据temp = G.vertices[i].firstarc;while(temp){printf("%d , ",temp->adjvex);temp = temp->next;}}else{printf(" %d号链表为空!",i);}}}

图如下:


运行结果:


0 0