竞赛常考的知识点大总结(七)图论

最短路

最短路问题(Shortest Path Problem)是图论中的一个经典问题,它要求在给定的图中找到两个顶点之间的最短路径。最短路问题可以是单源最短路问题(从一个顶点到其他所有顶点的最短路径)或所有对最短路问题(任意两个顶点之间的最短路径)。

特点:

1.图论问题:最短路问题是图论中的一个基本问题,通常在加权图中求解。

2.权重:图中的边具有权重,最短路问题的目标是最小化路径的权重总和。

3.多种算法:存在多种算法可以解决最短路问题,如迪杰斯特拉算法(Dijkstra's Algorithm)、贝尔曼-福特算法(Bellman-Ford Algorithm)、Floyd-Warshall算法等。

4.应用广泛:最短路问题在现实世界中有广泛的应用,如网络路由、交通规划、物流调度等。

常见用法:

1.网络路由:在网络设计中,最短路算法用于确定数据包的最佳传输路径。

2.交通规划:在交通规划中,最短路算法用于计算两点之间的最短行驶路径。

3.物流调度:在物流调度中,最短路算法用于优化货物的配送路径。

4.游戏开发:在游戏开发中,最短路算法用于AI寻路和地图探索。

经典C语言例题:

题目: 使用迪杰斯特拉算法解决单源最短路问题。

示例代码:

#include <stdio.h>
#include <limits.h>// 定义图的结构体
typedef struct Graph {int V; // 顶点数量int** adjMatrix; // 邻接矩阵
} Graph;// 创建图的函数
Graph* createGraph(int V) {Graph* graph = (Graph*)malloc(sizeof(Graph));graph->V = V;graph->adjMatrix = (int**)malloc(V * sizeof(int*));for (int i = 0; i < V; i++) {graph->adjMatrix[i] = (int*)malloc(V * sizeof(int));memset(graph->adjMatrix[i], INT_MAX, V * sizeof(int));graph->adjMatrix[i][i] = 0;}return graph;
}// 添加边的函数
void addEdge(Graph* graph, int src, int dest, int weight) {graph->adjMatrix[src][dest] = weight;graph->adjMatrix[dest][src] = weight; // 无向图
}// 迪杰斯特拉算法函数
void dijkstra(Graph* graph, int src) {int* dist = (int*)malloc(graph->V * sizeof(int));int* sptSet = (int*)malloc(graph->V * sizeof(int));for (int i = 0; i < graph->V; i++) {dist[i] = INT_MAX;sptSet[i] = 0;}dist[src] = 0;for (int count = 0; count < graph->V - 1; count++) {int u = -1, min = INT_MAX;for (int v = 0; v < graph->V; v++) {if (sptSet[v] == 0 && dist[v] <= min) {u = v;min = dist[v];}}sptSet[u] = 1;for (int v = 0; v < graph->V; v++) {if (sptSet[v] == 0 && graph->adjMatrix[u][v] && dist[u] != INT_MAX && dist[u] + graph->adjMatrix[u][v] < dist[v]) {dist[v] = dist[u] + graph->adjMatrix[u][v];}}}printf("Vertex\tDistance from Source\n");for (int i = 0; i < graph->V; i++) {printf("%d\t\t%d\n", i, dist[i]);}free(dist);free(sptSet);
}int main() {Graph* graph = createGraph(9);addEdge(graph, 0, 1, 4);addEdge(graph, 0, 7, 8);addEdge(graph, 1, 2, 8);addEdge(graph, 1, 7, 11);addEdge(graph, 2, 3, 7);addEdge(graph, 2, 8, 2);addEdge(graph, 2, 5, 4);addEdge(graph, 3, 4, 9);addEdge(graph, 3, 5, 14);addEdge(graph, 4, 5, 10);addEdge(graph, 5, 6, 2);addEdge(graph, 6, 8, 6);addEdge(graph, 6, 7, 1);addEdge(graph, 7, 8, 7);dijkstra(graph, 0);free(graph->adjMatrix[0]);free(graph->adjMatrix);free(graph);return 0;
}

例题分析:

1.创建图createGraph函数创建一个图的结构体,包括顶点数量和邻接矩阵。

2.添加边addEdge函数向图中添加边,并设置边的权重。

3.迪杰斯特拉算法dijkstra函数实现迪杰斯特拉算法,计算从源点src到其他所有顶点的最短路径。函数使用一个数组dist来存储到每个顶点的最短路径权重,另一个数组sptSet来标记已经找到最短路径的顶点。

4.打印结果:函数最后打印出每个顶点到源点的最短路径权重。

5.主函数:在main函数中,创建了一个图,并添加了一些边。调用dijkstra函数计算从顶点0到其他所有顶点的最短路径,并打印结果。

这个例题展示了如何在C语言中使用迪杰斯特拉算法解决单源最短路问题。通过这个例子,可以更好地理解迪杰斯特拉算法在解决最短路问题中的应用,以及如何使用邻接矩阵来存储图的信息。迪杰斯特拉算法是一种贪心算法,它通过逐步选择最短的未处理路径来找到最短路径,适用于加权图中的单源最短路问题。

树的直径

树的直径(Diameter of a Tree)是指树中任意两点之间的最长路径的长度。在图论中,树是一种特殊的无向图,它没有环,并且任意两个顶点之间有且仅有一条路径。

特点:

1.最长路径:树的直径是树中任意两点之间的最长路径的长度。

2.无环:树是一种无环的图,这意味着树中不存在循环依赖。

3.唯一路径:在树中,任意两个顶点之间有且仅有一条路径。

4.连通性:树中的任意两个顶点都是连通的。

常见用法:

1.网络设计:在计算机网络中,树的直径可以用来衡量网络的效率,最长路径越短,网络的响应时间越短。

2.数据结构:在数据结构中,树的直径可以用来衡量树的深度,有助于优化树的存储和查询效率。

3.算法设计:在算法设计中,树的直径可以用来衡量算法的性能,最长路径越短,算法的效率越高。

经典C语言例题:

题目: 计算树的直径。

示例代码:

#include <stdio.h>
#include <limits.h>// 定义树的结构体
typedef struct Node {int vertex;struct Node* left;struct Node* right;
} Node;// 创建树的节点
Node* newNode(int v) {Node* node = (Node*)malloc(sizeof(Node));node->vertex = v;node->left = NULL;node->right = NULL;return node;
}// 计算树的直径
int treeDiameter(Node* root) {if (root == NULL) {return 0;}// 计算左右子树的高度int leftHeight = treeDiameter(root->left);int rightHeight = treeDiameter(root->right);// 更新直径int diameter = leftHeight + rightHeight;// 返回当前子树的高度return (leftHeight > rightHeight) ? leftHeight + 1 : rightHeight + 1;
}// 主函数
int main() {Node* root = newNode(1);root->left = newNode(2);root->right = newNode(3);root->left->left = newNode(4);root->left->right = newNode(5);root->right->left = newNode(6);root->right->right = newNode(7);printf("Diameter of the tree is: %d\n", treeDiameter(root));return 0;
}

例题分析:

1.创建树的节点newNode函数创建树的节点,并初始化节点的值。

2.计算树的直径treeDiameter函数递归地计算树的直径。函数首先计算左右子树的高度,然后更新直径,最后返回当前子树的高度。

3.主函数:在main函数中,创建了一个树的实例,并调用treeDiameter函数计算树的直径,最后打印结果。

这个例题展示了如何在C语言中使用递归方法来计算树的直径。通过这个例子,可以更好地理解树的直径在解决树形结构问题中的应用,以及如何使用递归技术来高效地解决问题。树的直径是树中任意两点之间的最长路径的长度,通过计算左右子树的高度并更新直径,可以得到整个树的直径。

拓扑排序

拓扑排序(Topological Sorting)是图论中的一种算法,用于对有向无环图(DAG)的顶点进行排序,使得对于图中的每一条有向边(u, v),u在排序中都出现在v之前。拓扑排序通常用于解决依赖关系问题,如课程安排、任务调度等。

特点:

1.有向无环图:拓扑排序只适用于有向无环图,即图中不存在环。

2.排序结果:拓扑排序的结果可能不唯一,因为可能存在多个合法的排序。

3.依赖关系:拓扑排序反映了图中顶点之间的依赖关系,即如果存在一条路径从u到v,则u在排序中必须出现在v之前。

4.应用广泛:拓扑排序在编译器设计、软件工程、项目管理等领域都有广泛应用。

常见用法:

1.课程安排:在大学课程安排中,拓扑排序可以用来确定课程的先修关系。

2.任务调度:在项目管理中,拓扑排序可以用来确定任务的执行顺序。

3.依赖解析:在软件构建系统中,拓扑排序可以用来解析模块之间的依赖关系。

经典C语言例题:

题目: 使用拓扑排序解决课程安排问题。

示例代码:

#include <stdio.h>
#include <stdlib.h>// 定义图的结构体
typedef struct Graph {int V; // 顶点数量int* adjMatrix; // 邻接矩阵
} Graph;// 创建图的函数
Graph* createGraph(int V) {Graph* graph = (Graph*)malloc(sizeof(Graph));graph->V = V;graph->adjMatrix = (int*)malloc(V * V * sizeof(int));return graph;
}// 添加边的函数
void addEdge(Graph* graph, int src, int dest) {graph->adjMatrix[src * graph->V + dest] = 1;
}// 拓扑排序函数
void topologicalSort(Graph* graph, int V, int* order) {int* indegree = (int*)calloc(V, sizeof(int));for (int i = 0; i < V; i++) {for (int j = 0; j < V; j++) {if (graph->adjMatrix[i * V + j] == 1) {indegree[j]++;}}}int queue[V];int front = 0, rear = -1;for (int i = 0; i < V; i++) {if (indegree[i] == 0) {queue[++rear] = i;}}int count = 0;while (front <= rear) {int v = queue[front++];order[count++] = v;for (int i = 0; i < V; i++) {if (graph->adjMatrix[v * V + i] == 1 && --indegree[i] == 0) {queue[++rear] = i;}}}if (count != V) {printf("Graph has a cycle\n");free(indegree);free(queue);return;}printf("Topological order: ");for (int i = 0; i < count; i++) {printf("%d ", order[i]);}printf("\n");free(indegree);free(queue);
}int main() {Graph* graph = createGraph(6);addEdge(graph, 5, 2);addEdge(graph, 5, 0);addEdge(graph, 4, 0);addEdge(graph, 4, 1);addEdge(graph, 2, 3);addEdge(graph, 3, 1);int order[6];topologicalSort(graph, 6, order);return 0;
}

例题分析:

1.创建图createGraph函数创建一个图的结构体,包括顶点数量和邻接矩阵。

2.添加边addEdge函数向图中添加边。

3.拓扑排序topologicalSort函数实现拓扑排序算法。函数首先计算每个顶点的入度,然后将入度为0的顶点入队列。接着,从队列中取出顶点,将其加入排序结果,并将其所有出边对应的顶点的入度减1,如果入度变为0,则加入队列。最后,如果排序结果的顶点数量不等于图的顶点数量,则说明图中有环。

4.打印结果:函数最后打印出拓扑排序的结果。

5.主函数:在main函数中,创建了一个图,并添加了一些边。调用topologicalSort函数计算拓扑排序,并打印结果。

这个例题展示了如何在C语言中使用拓扑排序解决课程安排问题。通过这个例子,可以更好地理解拓扑排序在解决依赖关系问题中的应用,以及如何使用邻接矩阵来存储图的信息。拓扑排序是一种有效的算法,可以用来确定有向无环图中顶点的合法排序,从而解决依赖关系问题。

最小生成树

最小生成树(Minimum Spanning Tree,MST)是图论中的一个概念,它是指在一个加权连通图中,选取的边的权重之和最小,并且包括图中的所有顶点的生成树。最小生成树具有以下特点:

特点:

1.连通性:最小生成树包含图中的所有顶点。

2.无环:最小生成树是一棵树,因此它不包含任何环。

3.权重最小:最小生成树的边的权重之和是所有生成树中最小的。

4.唯一性:在权重不相等的图中,最小生成树是唯一的;如果图中存在权重相同的边,则可能存在多个最小生成树。

常见用法:

1.网络设计:在计算机网络中,最小生成树用于设计最经济的网络连接。

2.电路设计:在电路设计中,最小生成树用于寻找连接所有元件的最短路径。

3.城市规划:在城市规划中,最小生成树用于确定城市中各个区域的最短道路连接。

4.图像处理:在图像处理中,最小生成树用于图像分割和特征提取。

经典C语言例题:

题目: 使用普里姆算法(Prim's Algorithm)解决最小生成树问题。

示例代码:

#include <stdio.h>
#include <limits.h>// 定义图的结构体
typedef struct Graph {int V; // 顶点数量int** adjMatrix; // 邻接矩阵
} Graph;// 创建图的函数
Graph* createGraph(int V) {Graph* graph = (Graph*)malloc(sizeof(Graph));graph->V = V;graph->adjMatrix = (int**)malloc(V * sizeof(int*));for (int i = 0; i < V; i++) {graph->adjMatrix[i] = (int*)malloc(V * sizeof(int));memset(graph->adjMatrix[i], INT_MAX, V * sizeof(int));graph->adjMatrix[i][i] = 0;}return graph;
}// 添加边的函数
void addEdge(Graph* graph, int src, int dest, int weight) {graph->adjMatrix[src][dest] = weight;graph->adjMatrix[dest][src] = weight; // 无向图
}// 普里姆算法函数
void primMST(Graph* graph, int start) {int* key = (int*)malloc(graph->V * sizeof(int));int* parent = (int*)malloc(graph->V * sizeof(int));int* inMST = (int*)calloc(graph->V, sizeof(int));for (int i = 0; i < graph->V; i++) {key[i] = INT_MAX;parent[i] = -1;}key[start] = 0;parent[start] = -1;for (int count = 0; count < graph->V - 1; count++) {int u = -1, min = INT_MAX;for (int v = 0; v < graph->V; v++) {if (inMST[v] == 0 && key[v] <= min) {u = v;min = key[v];}}inMST[u] = 1;for (int v = 0; v < graph->V; v++) {if (graph->adjMatrix[u][v] && inMST[v] == 0 && graph->adjMatrix[u][v] < key[v]) {parent[v] = u;key[v] = graph->adjMatrix[u][v];}}}printf("Edge \tWeight\n");for (int i = 1; i < graph->V; i++) {printf("%d - %d \t%d\n", parent[i], i, graph->adjMatrix[i][parent[i]]);}free(key);free(parent);free(inMST);
}int main() {Graph* graph = createGraph(9);addEdge(graph, 0, 1, 4);addEdge(graph, 0, 7, 8);addEdge(graph, 1, 2, 8);addEdge(graph, 1, 7, 11);addEdge(graph, 2, 3, 7);addEdge(graph, 2, 8, 2);addEdge(graph, 2, 5, 4);addEdge(graph, 3, 4, 9);addEdge(graph, 3, 5, 14);addEdge(graph, 4, 5, 10);addEdge(graph, 5, 6, 2);addEdge(graph, 6, 8, 6);addEdge(graph, 6, 7, 1);addEdge(graph, 7, 8, 7);primMST(graph, 0);free(graph->adjMatrix[0]);free(graph->adjMatrix);free(graph);return 0;
}

例题分析:

1.创建图createGraph函数创建一个图的结构体,包括顶点数量和邻接矩阵。

2.添加边addEdge函数向图中添加边,并设置边的权重。

3.普里姆算法primMST函数实现普里姆算法,计算从源点start到其他所有顶点的最小生成树。函数使用三个数组keyparentinMST来存储每个顶点的最小权重、前驱顶点和是否在最小生成树中。

4.打印结果:函数最后打印出最小生成树的边和权重。

5.主函数:在main函数中,创建了一个图,并添加了一些边。调用primMST函数计算从顶点0到其他所有顶点的最小生成树,并打印结果。

这个例题展示了如何在C语言中使用普里姆算法解决最小生成树问题。通过这个例子,可以更好地理解普里姆算法在解决最小生成树问题中的应用,以及如何使用邻接矩阵来存储图的信息。普里姆算法是一种贪心算法,它通过逐步选择最小权重的边来构建最小生成树,适用于加权图中的最小生成树问题。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/786628.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Oracle 数据库中的全文搜索

Oracle 数据库中的全文搜索 0. 引言1. 整体流程2. 创建索引2-1. 创建一个简单的表2-2. 创建文本索引2-3. 查看创建的基础表 3. 运行查询3-1. 运行文本查询3-2. CONTAINS 运算符3-3. 混合查询3-4. OR 查询3-5. 通配符3-6. 短语搜索3-7. 模糊搜索&#xff08;Fuzzy searches&…

详细解释Javaweb、Spring和Spring Boot对数据库的使用

在传统的Javaweb中&#xff0c;对数据库进行访问通常使用JDBC&#xff08;Java Database Connectivity&#xff09;来实现。以下是一个简单的示例&#xff0c;演示如何使用JDBC连接数据库并执行查询操作&#xff1a; java import java.sql.Connection; import java.sql.Drive…

2021-08-06

yarn的简介&#xff1a; Yarn是facebook发布的一款取代npm的包管理工具。 yarn的特点&#xff1a; 速度超快。 Yarn 缓存了每个下载过的包&#xff0c;所以再次使用时无需重复下载。 同时利用并行下载以最大化资源利用率&#xff0c;因此安装速度更快。超级安全。 在执行代码…

ChatGPT技巧分享:如何用AI提升学术写作水平

ChatGPT无限次数:点击直达 ChatGPT技巧分享&#xff1a;如何用AI提升学术写作水平 在当今信息爆炸的时代&#xff0c;学术写作是一个重要的技能&#xff0c;但如何提高自己的学术写作水平呢&#xff1f;AI技术的发展为我们提供了更多可能&#xff0c;其中ChatGPT作为一种强大的…

Redis性能瓶颈与安全隐患排查验证纪实

在写《Redis怎样保证数据安全&#xff1f;》这篇文章&#xff0c;我是有对redis设置密码需要哪些步骤&#xff0c;设置密码的性能损耗有验证的。这就涉及到要对redis的配置做修改。 开始时我是打算采用直接使用redis配置文件的方式。所以我从redis官网下载了一个默认的配置文件…

ROS 2边学边练(9)-- 用launch命令管理启动项

概念 我们在前面的ROS 2体验过程中&#xff0c;一直拿小海龟这个例子来练手&#xff0c;过程比较轻松&#xff0c;因为只有两个节点&#xff08;/turtlesim和/teleop_turtle&#xff09;&#xff0c;只需打开两个终端&#xff0c;ros2 run 节点就ok&#xff0c;但&#xff0c;现…

Datacom HCIP笔记-ISIS协议

IS中间系统&#xff08;路由器/运行了ISIS协议的设备&#xff09; ES终端系统(PC,PAD,print) 网络功能模型 ISO定义 事实标准 OSI TCP/IP 网络层(CLNP) (IS-IS) 网络…

EfficientVMamba实战:使用EfficientVMamba实现图像分类任务(一)

文章目录 摘要安装包安装timm 数据增强Cutout和MixupEMA项目结构编译安装Vim环境环境安装过程安装库文件 计算mean和std生成数据集 摘要 论文&#xff1a;https://arxiv.org/pdf/2401.09417v1.pdf 作者研究了轻量级模型设计的新方法&#xff0c;通过引入视觉状态空间模型&…

每天学习一个Linux命令之wget

每天学习一个Linux命令之wget 简介 在Linux系统中&#xff0c;wget是一个使用非常广泛的命令行工具&#xff0c;用于从网络上下载文件。无论是从简单的文件下载&#xff0c;还是通过递归下载整个网站&#xff0c;wget都能帮助你完成。本文将详细介绍wget命令的用法及其可用的…

Git、TortoiseGit、SVN、TortoiseSVN 的关系和区别

Git、TortoiseGit、SVN、TortoiseSVN 的关系和区别 &#xff08;二&#xff09;Git&#xff08;分布式版本控制系统&#xff09;:&#xff08;二&#xff09;SVN&#xff08;集中式版本控制系统&#xff09;&#xff08;三&#xff09;TortoiseGit一、下载安装 git二、安装过程…

python如何处理文本错误

在python中&#xff0c;如果读取的文本文件不在程序的目录中&#xff0c;会提示FileNotFoundError 如果不能确定文本文件是否在目录中&#xff0c;可以用try except语句 代码如下 from pathlib import PathpathPath(alice.txt) try:contentspath.read_text(encodingutf_8) e…

Tomcat调优总结

Tomcat自身的调优是针对conf/server.xml中的几个参数的调优设置。首先是对这几个参数的含义要有深刻而清楚的理解。以tomcat8.5为例&#xff0c;讲解参数。 同时也得认识到一点&#xff0c;tomcat调优也受制于linux内核。linux内核对tcp连接也有几个参数可以调优。 因此可以将…

【C/C++】C语言实现串

C语言实现字符串 简单描述代码运行结果 简单描述 用codeblocks编译通过 源码参考连接 https://gitee.com/IUuaena/data-structures-c.git 代码 guistar_string.h #ifndef GUISTAR_STRING_H_INCLUDED #define GUISTAR_STRING_H_INCLUDED/*! brief 函数返回值枚举 */ typedef e…

scala实现通过Spark统计人均登录次数最终写入MySQL

谨以此博客作为记录 小编这里用的版本是&#xff1a; <hadoop.version>2.7.7</hadoop.version> <spark.version>2.4.5</spark.version> <scala.version>2.12.10</scala.version> 如果没用到Hadoop可以忽略 步骤 准备数据&#xff0c;知道…

C++面向对象程序设计 - 访问对象中成员的3种方法

在C程序中访问对象的成员变量和成员函数&#xff0c;有三种方法&#xff1a; 通过对象名和成员运算符访问对象中的成员&#xff1b;通过指向对象的指针访问对象中的成员&#xff1b;通过对象的引用变量访问对象中的成员 在了解访问对象中成员的3种方法前&#xff0c;先了解下C…

StarRocks部署

介绍 tarRocks 是新一代极速全场景 MPP (Massively Parallel Processing) 数据库。StarRocks 的愿景是能够让用户的数据分析变得更加简单和敏捷。用户无需经过复杂的预处理&#xff0c;就可以用 StarRocks 来支持多种数据分析场景的极速分析。 官网 ## 部署 https://docs.sta…

速盾:cdn加速接口会被劫持吗?

CDN&#xff08;Content Delivery Network&#xff09;加速接口是一种常用的网络加速技术&#xff0c;通过将静态资源分发到全球多个节点&#xff0c;提高资源的访问速度和稳定性。然而&#xff0c;随着互联网的发展&#xff0c;网络安全问题也日益突出&#xff0c;因此人们对于…

网络安全之IP地址证书的重要性

在数字化时代&#xff0c;网络空间已成为各类活动的重要载体&#xff0c;无论是商业交易、信息交流还是远程办公&#xff0c;都离不开互联网的支撑。然而&#xff0c;网络环境的开放性与匿名性也带来了安全风险&#xff0c;如何确保网络交互中的身份真实可信&#xff0c;成为了…

【御控物联】JSON结构数据转换在物联业务中应用(场景案例二)

文章目录 一、物联网业务场景现状二、物联网业务场景数据交互格式三、JSON格式数据转换案例四、JSON数据格式转换DEMO五、在线转换工具六、技术资料 一、物联网业务场景现状 目前&#xff0c;市场上多数物联网关与物联平台捆绑售卖&#xff0c;网关采集到设备数据只能按照指定…

Excel·VBA二维数组组合函数之穷举推理题

看到一个帖子《CSDN-求助一道推理题》&#xff0c;与之前《python穷举暴力破解《2018年刑侦推理题》用python穷举的推理题很类似 那么是否可以使用《ExcelVBA二维数组组合函数、组合求和》combin_arr2d函数&#xff0c;生成结果进行穷举呢&#xff1f; Sub 穷举推理题()Dim …