首页 > 编程语言 >图Graph及相关算法(Dijkstra,Kruskal)

图Graph及相关算法(Dijkstra,Kruskal)

时间:2024-03-21 16:04:12浏览次数:17  
标签:int Graph Kruskal v1 Dijkstra v4 nV pGraph pMark

目录

无向图

有向图

邻接矩阵

邻接表

图的bfs,dfs

二部图(二分图)

有向无环图(DAG)

拓扑排序(Topological Sort)

AOV网

迪杰斯特拉Dijkstra

最小生成树

克鲁斯卡尔:Kruskal

普里姆:prim


图是多对多关系,是顶点和边的二元组和。

无向图

1.依附关系:边(v1,v2)依附于顶点v1,v2。

2.完全图:所有可能的边都存在C_{n}^{2}

3.路径:一个点到另一个点的边。

4.简单路径:除起点终点可能相同外,其他点不允许重复出现。

5.连通:有路径可通。(有n个点,可能联通需要n-1条边,一定能联通C_{n-1}^{2}+1,拿掉一个点完全联通图+1)

6.连通图:图中所有点之间均有路径可通。

7.子图:子图顶点集合\epsilon原顶点集合,边集合\epsilon边集合。

8.极大连通子图(连通分量):画圈的就是。

有向图

1.连通图:相异成对顶点间路径可通。

2.极大连通子图(强连通分量):成对顶点间均有路径可通。

3.用<v1,v2>。

邻接矩阵

边多适用,唯一。

12345
101110
210101
311011
410101
501110

邻接表

边少适用,不唯一。

图的bfs,dfs

图的创建:(1)顶点个数(2)申请并初始化(3)放边

DFS:(1)标记数组(2)遍历:1.打印顶点2.标记(3)标记邻接点,找邻接的未处理过的同(2)

BFS:(1)Queue(2)标记初始化(3)起始顶点入队标记(4)处理:弹出,打印,遍历邻接点,未处理邻接点入队,标记,等待处理重复(4)

#include<iostream>
#include<string.h>
#include<queue>
using namespace std;
typedef struct node
{ 
	int nedge;
	int nV;
	int* pjuzhen;
}Graph;
Graph* Create()
{
	Graph* pGraph = (Graph*)malloc(sizeof(Graph));
	//顶点个数,边的条数
	int nv, ne;
	cin >> nv >> ne;
	pGraph->nedge = ne;
	pGraph->nV = nv;
	pGraph->pjuzhen = (int*)malloc(sizeof(Graph) * nv * nv);
	memset(pGraph->pjuzhen, 0, sizeof(Graph) * nv * nv);
	for (int i = 0; i < ne; i++)
	{
		int v1, v2;
		cin >> v1 >> v2;
		if (v1>=1&& v1<=nv&&v2>=1&&v2<=nv&&v1!=v2&&pGraph->pjuzhen[(v1 - 1) * nv + v2 - 1] == 0)
		{
			pGraph->pjuzhen[(v1 - 1) * nv + v2 - 1] = 1;
			pGraph->pjuzhen[(v2 - 1) * nv + v1 - 1] = 1;
		}
		else i--;
	}
	return pGraph;
}
void DFSGraph(Graph* pGraph, int fir, int* pMark)
{
	cout << fir << " ";
	pMark[fir - 1] = 1;
	for (int i = 0; i < pGraph->nV; i++)
	{
		if (pGraph->pjuzhen[(fir - 1) * pGraph->nV + i] == 1 && pMark[i] == 0)
		{
			DFSGraph(pGraph, i + 1, pMark);
		}
	}
}
void BFS(Graph* pGraph, int fir)
{
	if (pGraph == NULL || fir<1 || fir>pGraph->nV)return;
	int* pMark = NULL;
	pMark = (int*)malloc(sizeof(int) * pGraph->nV);
	memset(pMark, 0, sizeof(int) * pGraph->nV);
	queue<int>q;
	q.push(fir);
	pMark[fir - 1] = 1;
	while (!q.empty())
	{
		fir = q.front();
		q.pop();
		cout << fir << " ";
		for (int i = 0; i < pGraph->nV; i++)
		{
			if (pGraph->pjuzhen[(fir - 1) * pGraph->nV + i] == 1 && pMark[i] == 0)
			{
				q.push(i + 1);
				pMark[i] = 1;
			}
		}
	}free(pMark);
	pMark = NULL;
}
void DFS(Graph* pGraph,int fir)
{
	if (pGraph == NULL || fir < 1 || fir>pGraph->nV)return;
	int* pMark=NULL;
	pMark = (int*)malloc(sizeof(int)*pGraph->nV);
	memset(pMark, 0, sizeof(int) * pGraph->nV);
	DFSGraph(pGraph, fir, pMark);
	free(pMark);
	pMark = NULL;
}
int main()
{
	Graph* p = Create();
	for (int i = 0; i < p->nV * p->nV; i++)
	{
		if (i % p->nV == 0)cout << endl;
		cout << p->pjuzhen[i] << " ";
	}
	cout << endl;
	DFS(p, 2);
	cout << endl;
	BFS(p, 4);
	cout << endl;
	return 0;
}

二部图(二分图)

G=(u,v,e),u,v都是顶点集合,边是发生在集合之间的,但是集合内部没边关系。

例如:这个就不是,因为v2和v4是一个集合的它们相连了。

例如:这个就是。

有向无环图(DAG)

例:

有向无环图一定有拓扑排序。

拓扑排序(Topological Sort)

为一个项目内具各依赖关系的活动求得可执行的线性顺序。这个线性顺序叫拓扑序列。

拓扑序列:若从顶点vi到vj有一条路径,则在顶点的拓扑序列中顶点vi必在顶点vj之前。

有拓扑排序的一定是DAG。

AOV网

AOV没有回路的前提下,可以将全部活动排序列成拓扑序列。

步骤:

(1)统计所有顶点入度。

(2)创建队列。

(3)入度为0的节点入队。

(4)处理 :出队,所有邻接点的入度更新,新的入度为0的节点入队。

迪杰斯特拉Dijkstra

点到点的最短路径:

v1v2v3v4
v10760
v2120229
v311500
v402360

这里写一下v1到各个点的最短距离。

v1{0,7,6,0}                 (找数最小不为0的点)

v1,v3{0,7,6,0}           (v3->v2为5,5+6<7,所以为7,v3到不了v4还是为0)

v1,v3,v2{0,7,6,16}    (v2->v4为9,9+7=16)

最小生成树

克鲁斯卡尔:Kruskal

按路径长度从小到大排序,如果两点已经连通就跳过。

例:

先是3,4,5,6路径连上。

由于v4,v7已经联通所以跳过11。

连上15,20,结束。

普里姆:prim

假设从v1节点寻找。

v1->v3,v1->v4,v1->v8中v1->v8最小。

v1->v3,v1->v4,v8->v7中v8->v7最小,所以选v8->v7。

v1->v3,v1->v4,v7->v4,v7->v6中,v1->v4最小,选v1->v4。

v1->v3,v4->v3,v4->v5,v4->v6,v7->v6中,v4->v3最小,选v4->v3。

后续同理(由于v4,v7已经连通所以看下一个15)。

结果:

标签:int,Graph,Kruskal,v1,Dijkstra,v4,nV,pGraph,pMark
From: https://blog.csdn.net/qq_60924211/article/details/136887252

相关文章

  • 机器人路径规划:基于迪杰斯特拉算法(Dijkstra)的机器人路径规划(提供Python代码)
    迪杰斯特拉算法(Dijkstra)是由荷兰计算机科学家狄克斯特拉于1959年提出的,因此又叫狄克斯特拉算法。是从一个顶点到其余各顶点的最短路径算法,解决的是有权图中最短路径问题。迪杰斯特拉算法主要特点是从起始点开始,采用贪心算法的策略,每次遍历到始点距离最近且未访问过的顶点的邻......
  • dijkstra算法详解
    今天给大家讲解\(dijkstra\)图论最短路算法在讲解\(dijkstra\)算法之前,先来给大家讲解一下图论中的松弛操作。松弛,即\(relaxtion\),是一种编程学术语。举例说明,例如我们可以从某个机场坐飞机达到若干个机场,然后从这些机场出发,我们又需做火车前往若干个城镇。现在假设我们手里......
  • Learning Disentangled Graph Convolutional Networks Locally and Globally论文阅读
    LearningDisentangledGraphConvolutionalNetworksLocallyandGlobally论文阅读笔记Abstract存在的问题:​ 尽管现有的gcn取得了成功,但它们通常忽略了现实世界图中通常出现的纠缠潜在因素,这导致了无法解释的节点表示。更糟糕的是,虽然重点放在局部图信息上,但整个图的全局知......
  • GraphQL入门之分页查询
    前一篇文章讲了怎么创建GraphQL的查询操作,今天在此基础上看看要实现一个简单的分页查询应该怎么做,顺便可以介绍一下GraphQL里的枚举类型和查询参数应该怎么用。创建Node.js的工程mkdirmyappcdmyappnpminit(一路回车)安装依赖包npminstall@apollo/server......
  • 算法详解——Dijkstra算法
      Dijkstra算法的目的是寻找单起点最短路径,其策略是贪心加非负加权队列一、单起点最短路径问题  单起点最短路径问题:给定一个加权连通图中的特定起点,目标是找出从该起点到图中所有其他顶点的最短路径集合。需要明确的是,这里关心的不仅仅局限于寻找一条从起点出发到任......
  • 零门槛打造个人图床:感谢Telegraph-Image
    零门槛打造个人图床:感谢Telegraph-Image更好的阅读体验?幕前小话很早之前,我就用GitHub和Cloudflare搭建了自己的图床,不过没多久就发现cf自带的dev域名被墙了,于是就没再管它。直到上周,我在课上无聊时用手机随便翻了翻后台,没想到竟然又能打开了!并且后台多出了200多张网友......
  • 机器人路径规划:基于迪杰斯特拉算法(Dijkstra)的机器人路径规划(提供Python代码)
    迪杰斯特拉算法(Dijkstra)是由荷兰计算机科学家狄克斯特拉于1959年提出的,因此又叫狄克斯特拉算法。是从一个顶点到其余各顶点的最短路径算法,解决的是有权图中最短路径问题。迪杰斯特拉算法主要特点是从起始点开始,采用贪心算法的策略,每次遍历到始点距离最近且未访问过的顶点的邻......
  • 论文解读(CGC)《Generating Counterfactual Hard Negative Samples for Graph Contrasti
    Note:[wechat:Y466551|可加勿骚扰,付费咨询]论文信息论文标题:GeneratingCounterfactualHardNegativeSamplesforGraphContrastiveLearning论文作者:论文来源:2023WWW论文地址:download 论文代码:download视屏讲解:click0-摘要图对比学习已经成为一种强大的无监督图......
  • Linux Graphics Stack(图图图)
    Linux图形相关涉及到硬件、内核驱动、协议API、2D/3D渲染框架、GUI框架、桌面环境等,相当复杂,这里简单收集架构图作为记录。1硬件相关显示相关的有:Displaying:显示器、投影等。包括Displayengine、Timingscontroller、DisplayinterfacePHY。Rendering:3Drendering,2Dsha......
  • KGAT Knowledge Graph Attention Network for Recommendation
    目录概符号说明KGATEmbeddingLayerAttentiveEmbeddingPropagationLayers代码WangX.,HeX.,CaoY.,LiuM.andChuaT.KGAT:Knowledgegraphattentionnetworkforrecommendation.KDD,2019.概知识图谱for推荐系统.符号说明\(\mathcal{G}_1=\{(u,y_{ui}......