算法设计与分析 作业二 答案与解析

题目一

涉及考点

邻接矩阵

方便找到是否有边 顶点的度

但是空间复杂度高 对于统计边的数量只能枚举

入度:竖 出度:横

邻接表

深度优先搜索 DFS

基于栈的访问

算法复杂度

时间复杂度:O(n) 每个节点都被访问

空间复杂度:最坏O(n)。AVL树O(logn)

用于生成括号-子集枚举-N皇后问题

搜索所有可能路径

广度优先搜索 BFS

基于队列的访问

先进先出-离得近的先访问

算法复杂度

空间复杂度:对于平衡二叉树,一般存入队列的是一层的内容,不超过树高logn;对于普通搜索树则是O(N)

题目与解析

题目二

涉及考点

克鲁斯卡尔最小生成树ElogE

创建并查集类

包括find check两个函数,check通过find找到两个连通分支各自的代表元

如果一致则返回false,否则true

在主函数中,创建目标队列 与 uf对象

对每一条边遍历,根据权重排序,每次提取最小的边,

对其顶点进行判断,调用uf对象的check函数,如果返回true则证明为两个分支,可以选择,否则continue

直到n-1

这就设计了连通性判断,因此需要上面并查集的内容

这样的操作包括:

1.判断是否成环------是否联通 root_x=self.find(x) root_y=self.find(y) root_x == root_y?

2.将一条边加入生成树中------union()

先创建UF集合,会自动拆为最小节点

然后堆边进行sort 复杂度logE,然后对于每条边进行判断:

如果uf.union能够执行,也就是UF输出True,不成环的情况下,就往mst中添加这条边,同时累加权重

直到mst的len=n-1

时间复杂度:

Prim最小生成树算法ElogV

创建邻接表、最小堆 目标队列 已访问 原始节点队列

创建结构体 包括起点 终点 权重

遍历所有边将其连接的点存入邻接表

初始时选择任意一个节点,探索其边,选择最小权重边,查看邻接表其终点是否在已访问列表中

如果没有则添加,并累计权重

同时将邻居节点的相邻边放入最小堆

开辟最小堆,维护当前可用探索的边,由于每次探索最小的,因此使用最小堆

开辟结果列表维护选取的边

开辟以访问集保存已经访问的顶点

开辟nodes集保存未访问的节点

'

nodes用于存放当前可用访问的节点

visited存放已经访问的顶点

mst保存结果边 weight保存总权重

min_heap维护当前可选边

对于传入的每一条边,对于第一个顶点graph[u]添加权重为w,目的为v

对于第二个顶点graph[v]添加权重为w,目的为u

随机选一个起点。

将其放入已访问列表visited,然后把start顶点可连出去的所有边放入最小堆,堆会自动按权重从小到大排序

对于每一轮,取出堆中最小的边,如果其目标顶点没有访问过,就将其添加到visied中,然后将这条边放进mst目标列表中,同时累加权重

对于这条新加入顶点考虑,对于新顶点的其他边连接的节点,如果没有访问过,就全部放入堆中

直到n-1条边都被访问了

时间复杂度:

对于堆的处理复杂度都是logV 每条边最多被加入堆一次,因此堆操作数不超过E次,因此复杂度是O(ElogV)

题目与解析

题目三

涉及考点

单元最短路 BellmanFord(可解决负权边)

依次遍历所有节点的所有边,即A->B A->C A->D,然后B->E C->B C->E。。。
重复V-1轮一定收敛,可能提前收敛

算法复杂度:O(V*E)

性质

要做V-1次遍历,因为有V-1条边

每一轮要松弛所有的边

要做多少轮?V-1

检测负环是否存在?

更新到第V-1次后收敛,不再更新。

为什么要V-1条边?

因为任意两个节点的最短路径最多包含V-1条边,如果出现环说明两条路必定存在一最短路。

题目与解析

一句话就是:列边松弛列DPi

列出所有可达边,然后一直松弛,遍历所有边后列DΠ表

最多需要遍历最短路径长度的边的轮数,每轮复杂度E

题目四

涉及考点

带虚拟节点的单源最短路

OJ作业有一道灌溉农田的题基本一样,这里把抽水机的价格换位等待时间即可

题目与解析

题目五

涉及考点

Floyd-Warshall 动态规划(来源数据结构)

D法是单源算法,如果要全源则需要n次

FW能一次性计算出所有点之间的最短路径

通过一张加权表和一张前驱表不断更新得到

distx是邻接矩阵,表达任意两点之间的最短距离

nextx是前驱表,记录下一跳

通过三层循环,选择kij,k是中继节点,i是起始,j是终点

不断更新k,相当于在任意两个节点之间插入另一个节点,看看有没有更短通路

更新n轮后一定会收敛

只要对角线为正,就证明没有负权环

对于最终表,从2->3,先看next4,由0,为下一条,那么下一步就是0->3,是1,然后是1->3,找到最短路径2-0-1-3. 距离是dist4 2->3=4

算法复杂度:

Floyd-Warshall 算法(来源算法设计)

对于01背包好用,物品当作节点

题目与解析

技巧:

1.k=1和k=4时可以用瞪眼法
2.k=1时 第一行 k=4时第四行不用更新
3.当(a,b+c)结构的b为0或无穷时不用更新

很简单,就是把在这个算法上多加一个前驱矩阵即可,用vector套vector初始化一个二维矩阵,然后D<-W初始化要额外说明对Pi的初始化。后面就是常规的FW。空间就是V*V

相关推荐
玛丽莲茼蒿1 小时前
Leetcode hot100 每日温度【中等】
算法·leetcode·职场和发展
cjp5601 小时前
009.UG二次开发,任务环境草图优化3(高级功能生成直线)
算法
样例过了就是过了2 小时前
LeetCode热题100 分割等和子集
数据结构·c++·算法·leetcode·动态规划
逻辑驱动的ken2 小时前
Java高频面试考点18
java·开发语言·数据库·算法·面试·职场和发展·哈希算法
北顾笙9802 小时前
day38-数据结构力扣
数据结构·算法·leetcode
m0_629494732 小时前
LeetCode 热题 100-----14.合并区间
数据结构·算法·leetcode
xin_nai2 小时前
LeetCode热题100(Java)(5)普通数组
算法·leetcode·职场和发展
旖-旎3 小时前
深搜练习(组合)(5)
c++·算法·深度优先·力扣
@小码农3 小时前
2026年3月Scratch图形化编程等级考试一级真题试卷
开发语言·数据结构·c++·算法