图->存储结构->邻接表
文字描述
邻接表是图的一种链式存储结构。在邻接表中,对图中每个顶点建立一个单链表,第i个单链表的结点表示依附顶点vi的边(对有向图是指以顶点vi为尾的弧)。单链表中的每个结点由3个域组成,其中邻接点域adjvex指示与顶点vi邻接的点在图中的位置;链域nextarc指示下一条边或弧的结点;数据域info存储和边或弧相关的信息如权值等。每个链表上附设一个表头结点,在表头结点中,除了设有链域firstarc指向链表中第一个结点外,还设有存储顶点vi的名或其他有关信息的数据域data。
在无向图的邻接表中,顶点vi的度恰为第i个单链表中的结点数;而在有向图中,第i个链表中的结点数只是顶点vi的出度,为求入度,需便历整个邻接表;为了方便确定顶点的入度或以顶点vi为头的弧,可以建立一个有向图的逆邻接表,即对每个顶点vi建立一个了链接以vi为头的弧的表。
示意图
算法分析
在建立邻接表或逆邻接表时,若输入的顶点信息就是顶点的编号,则建立邻接表的时间复杂度为n+e;否则,需要通过查找才能得到顶点在图中位置,则时间复杂度为n*e.
在邻接表上容易找到任一顶点的第一个邻接点和下一个领接点,但要判定任意两个顶点(vi和vj)之间是否有边或弧相连,则需搜索第i个或第j个链表;因此,不及邻接矩阵方便。
代码实现
/*
以邻接表作为图的存储结构创建图。
*/ #include <stdio.h>
#include <stdlib.h>
#include <string.h> #define INFINITY 100000 //最大值
#define MAX_VERTEX_NUM 20 //最大顶点数
#define None -1
typedef enum {DG, DN, UDG, UDN} GraphKind; //{有向图,有向网,无向图,无向网}
typedef char VertexType;
typedef struct{
char note[];
}InfoType;
//表结点
typedef struct ArcNode{
int adjvex; //该弧所指向的顶点的位置
struct ArcNode *nextarc; //指向下一条弧的指针
InfoType *info; //该弧相关信息的指针
}ArcNode;
//头结点
typedef struct VNode{
VertexType data;//顶点信息
ArcNode *firstarc;//指向第一条依附该顶点的弧的指针
}VNode, AdjList[MAX_VERTEX_NUM];
typedef struct{
AdjList vertices;
int vexnum;//图的顶点数
int arcnum;//图的弧数
int kind; //图的种类标志
}ALGraph; /*
若G中存在顶点u,则返回该顶点在图中位置;否则返回-1。
*/
int LocateVex(ALGraph G, VertexType v)
{
int i = ;
for(i=; i<G.vexnum; i++){
if(G.vertices[i].data == v){
return i;
}
}
return -;
} /*
在链表L的头部前插入v
*/
int InsFirst(ArcNode *L, int v)
{
ArcNode *n = (ArcNode *)malloc(sizeof(struct ArcNode));
n->adjvex = v;
n->nextarc = L->nextarc;
L->nextarc = n;
return ;
} /*
采用邻接表的存储结构,构造无向图
*/
int CreateUDG(ALGraph *G)
{
int i = , j = , k = , IncInfo = ;
int v1 = , v2 = ;
char tmp[] = {}; printf("输入顶点数,弧数,其他信息标志位: ");
scanf("%d,%d,%d", &G->vexnum, &G->arcnum, &IncInfo); for(i=; i<G->vexnum; i++){
printf("输入第%d个顶点: ", i+);
memset(tmp, , sizeof(tmp));
scanf("%s", tmp);
G->vertices[i].data = tmp[];
G->vertices[i].firstarc = malloc(sizeof(struct ArcNode));
G->vertices[i].firstarc->adjvex = None;
G->vertices[i].firstarc->nextarc = NULL;
} for(k=; k<G->arcnum; k++){
printf("输入第%d条弧(顶点1, 顶点2): ", k+);
memset(tmp, , sizeof(tmp));
scanf("%s", tmp);
sscanf(tmp, "%c,%c", &v1, &v2);
i = LocateVex(*G, v1);
j = LocateVex(*G, v2);
InsFirst(G->vertices[i].firstarc, j);
InsFirst(G->vertices[j].firstarc, i);
if(IncInfo){
//other info on arc
}
}
return ;
} /*
采用邻接表的存储结构,构造图
*/
int CreateGraph(ALGraph *G)
{
printf("输入图类型: -有向图(0), -有向网(1), +无向图(2), -无向网(3): ");
scanf("%d", &G->kind);
switch(G->kind){
case DG:
case DN:
case UDN:
printf("还不支持!\n");
return -;
case UDG:
return CreateUDG(G);
default:
return -;
}
} /*
输出图的信息
*/
void printG(ALGraph G)
{
if(G.kind == DG){
printf("类型:有向图;顶点数 %d, 弧数 %d\n", G.vexnum, G.arcnum);
}else if(G.kind == DN){
printf("类型:有向网;顶点数 %d, 弧数 %d\n", G.vexnum, G.arcnum);
}else if(G.kind == UDG){
printf("类型:无向图;顶点数 %d, 弧数 %d\n", G.vexnum, G.arcnum);
}else if(G.kind == UDN){
printf("类型:无向网;顶点数 %d, 弧数 %d\n", G.vexnum, G.arcnum);
}
int i = ;
ArcNode *p = NULL;
for(i=; i<G.vexnum; i++){
printf("%c\t", G.vertices[i].data);
p = G.vertices[i].firstarc;
while(p){
if(p->adjvex != None)
printf("%d\t", p->adjvex);
p = p->nextarc;
}
printf("\n");
}
return;
} int main(int argc, char *argv[])
{
ALGraph G;
if(CreateGraph(&G) > -){
printG(G);
}
return ;
}
邻接表存储结构(图)
代码运行
图->存储结构->邻接表的更多相关文章
- 图->存储结构->邻接多重表
文字描述 邻接多重表是无向图的另一种链式存储结构. 虽然邻接表是无向图的一种很有效的存储结构,在邻接表中容易求得顶点和边的各种信息. 但是,在邻接表中每一条边(vi,vj)有两个结点,分别在第i个和第 ...
- 图的bfs遍历模板(邻接矩阵存储和邻接表存储)
bfs遍历图模板伪代码: bfs(u){ //遍历u所在的连通块 queue q; //将u入队 inq[u] = true; while (q非空){ //取出q的队首元素u进行访问 for (从u ...
- 图->存储结构->十字链表
文字描述 十字链表是有向图的另一种链式存储结构. 在十字链表中,对应于有向图中每一条弧有一个结点,对应于每个顶点也有一个结点.这些结点的结构如下所示: 在弧结点中有5个域: 尾域tailvex和头域h ...
- 图->存储结构->数组表示法(邻接矩阵)
文字描述 用两个数组分别存储顶点信息和边/弧信息. 示意图 算法分析 构造一个采用邻接矩阵作存储结构.具有n个顶点和e条边的无向网(图)G的时间复杂度是(n*n + e*n), 其中对邻接矩阵G.ar ...
- 图的建立——邻接表表示(C语言+VC6.0平台)
图是一种重要而且相对复杂的数据结构,在实际编程中非常有用.邻接表是图的主要表示形式之一,是一种链接表表示方法. #include<stdio.h> #include<stdlib.h ...
- 数据结构与算法之PHP用邻接表、邻接矩阵实现图的广度优先遍历(BFS)
一.基本思想 1)从图中的某个顶点V出发访问并记录: 2)依次访问V的所有邻接顶点: 3)分别从这些邻接点出发,依次访问它们的未被访问过的邻接点,直到图中所有已被访问过的顶点的邻接点都被访问到. 4) ...
- 数据结构之---C语言实现图的邻接表存储表示
// 图的数组(邻接矩阵)存储表示 #include <stdio.h> #include <stdlib.h> #include <string.h> #defi ...
- 图的dfs遍历模板(邻接表和邻接矩阵存储)
我们做算法题的目的是解决问题,完成任务,而不是创造算法,解题的过程是利用算法的过程而不是创造算法的过程,我们不能不能陷入这样的认识误区.而想要快速高效的利用算法解决算法题,积累算法模板就很重要,利用模 ...
- 图的存储结构与操作--C语言实现
图(graph)是一种比树结构还要复杂的数据结构,它的术语,存储方式,遍历方式,用途都比较广,所以如果想要一次性完成所有的代码,那代码会非常长.所以,我将分两次来完成图的代码.这一次,我会完成图的五种 ...
随机推荐
- Python 读取csv的某行
站长用Python写了一个可以提取csv任一列的代码,欢迎使用.Github链接 csv是Comma-Separated Values的缩写,是用文本文件形式储存的表格数据,比如如下的表格: 就可以存 ...
- one-to-all及all-to-all网络通信模式
在这两种模式下,因为 占用的通信通道非常高,形成了一个一对多的通道 甚至是多对多的通道,导致现有的fattree网络结构负载太大.
- python中的selectors模块
它的功能与linux的epoll,还是select模块,poll等类似:实现高效的I/O multiplexing, 常用于非阻塞的socket的编程中: 简单介绍一下这个模块,更多内容查看 pyt ...
- 牛客网_Go语言相关练习_选择题(2)
注:题目来源均出自牛客网. 一.选择题 Map(集合)属于Go的内置类型,不需要引入其它库即可使用. Go-Map_菜鸟教程 在函数声明中,返回的参数要么都有变量名,要么都没有. C选项函数声明语法有 ...
- Nginx 实现负载均衡
.安装nginx和tomcat 我这里是使用docker安装的.安装流程可参照 dockerfile 这里安装了两个tomcat,端口分别是42000和42001.第二个tomcat的首页随便加了些代 ...
- Angular4学习笔记(三)- 路由
路由简介 路由是 Angular 应用程序的核心,它加载与所请求路由相关联的组件,以及获取特定路由的相关数据.这允许我们通过控制不同的路由,获取不同的数据,从而渲染不同的页面. 相关的类 Routes ...
- win7下安装Office2010老是出现提示安装MSXML6.10.1129.0,下载官方MSXML后提示安装成功却也安装不了
在注册表中增加以下信息: [HKEY_CLASSES_ROOT\TypeLib\{F5078F18-C551-11D3-89B9-0000F81FE221}][HKEY_CLASSES_ROOT\Ty ...
- Keras查看model weights .h5 文件的内容
Keras的模型是用hdf5存储的,如果想要查看模型,keras提供了get_weights的函数可以查看: for layer in model.layers: weights = layer.ge ...
- IntelliJ IDE破解
1.购买正版用户 2.激活码 一:下载以下jar,放到 bin 破解补丁无需使用注册码,下载地址 idea14 keygen下载地址 二:在下面两个文件中加入-javaagent:E:\IDEA\In ...
- 中检测到有潜在危险的 Request.Form 值。
两步 一.在</system.web>之前加上<httpRuntime requestValidationMode="2.0" /> <httpRun ...