图:广度优先遍历(BFS)和深度优先遍历(DFS)

1.工具类:队列和字典

export class DictionNary {// 字典的封装constructor() {this.items = {}}set(key, value) {// 添加键this.items[key] = value}has(key){// 判断键是否存在return this.items.hasOwnProperty(key)}get(key){// 获取键的valuereturn this.has(key) ? this.items[key] : undefined}remove (key){// 删除键if(this.has(key)){delete this.items[key]return true}return false}keys(){// 获取所有的键return Object.keys(this.items)}values(){// 获取所有的值return Object}size(){// 获取键值对的数量return this.keys().length}clear(){// 清空字典this.items = {}}toString(){// 转换为字符串if(this.size() > 0){let objString = `{${this.keys().join(',')}}`return objString}else{return '{}'}}
}export class Queue {// 队列的封装constructor() {this.items = []}// 方法enqueue(element) {// 添加元素到队列this.items.push(element)}dequeue() {// 移除队列的第一个元素return this.items.shift()}front() {// 返回队列的第一个元素return this.items[0]}isEmpty() {// 判断队列是否为空return this.items.length == 0}size() {// 返回队列的元素个数return this.items.length}toString() {return this.items.toString()}}

2. 图的封装

class Graph {constructor() {// 顶点this.vertexes = []// 边this.edges = new DictionNary()}// 方法addVertex(v){// 添加顶点this.vertexes.push(v)// 顶点对于边数组的初始化this.edges.set(v, [])}addEdge(v1, v2){// 无向图中边的设置this.edges.get(v1).push(v2)this.edges.get(v2).push(v1)}toString(){let result = ''for(let i = 0; i < this.vertexes.length; i++){result += this.vertexes[i] + ' -> 'const neighbors = this.edges.get(this.vertexes[i])for(let j = 0; j < neighbors.length; j++){result += neighbors[j] + ' '}result += '\n'}return result}initializeColor(){// 顶点遍历颜色初始化const colors = []for(let i = 0; i < this.vertexes.length; i++){colors[this.vertexes[i]] = 'white'}return colors}bfs(firstVertex, callback){// 广度优先遍历// 顶点遍历测试// 1.层序遍历:Breadth-First Search (BFS)// 2.深度遍历:Depth-First Search (DFS)// 3.为了记录顶点是否被访问过,我们使用三种颜色定义顶点的状态// 1.白色:表示该顶点还没有被访问// 2.灰色:表示该顶点被访问过,但并未被探索(被探索意思是其所有相邻顶点都被访问过)// 3.黑色:表示该顶点被访问过且被完全探索// 1.初始化顶点颜色const colors = this.initializeColor()// 2.创建队列const queue = new Queue()// 3.将第一个顶点加入队列queue.enqueue(firstVertex)// 4.循环遍历队列while(!queue.isEmpty()){// 4.1.从队列中取出一个顶点const v = queue.dequeue()// 4.2.获取和该顶点相邻的顶点const neighbors = this.edges.get(v)// 4.3.将当前顶点的颜色设置为灰色(被访问过)   colors[v] = 'gray'// 4.4.遍历该顶点的所有相邻顶点for(let i = 0; i < neighbors.length; i++){const w = neighbors[i]if(colors[w] === 'white'){colors[w] = 'gray'queue.enqueue(w) }}// 4.5.将当前顶点设置为黑色(被探索)colors[v] = 'black'// 4.6.调用callback函数callback(v)}}dfs(initVertex, callback){// 1.初始化颜色const colors = this.initializeColor()// 2.递归函数this.dfsVisit(initVertex, colors, callback)}dfsVisit(vertexes, colors, callback){// 1.访问过节点置灰色colors[vertexes] = 'gray'// 2.调用callback函数callback(vertexes)// 3.获取和该顶点相邻的顶点const neighbors = this.edges.get(vertexes)for(let i = 0; i < neighbors.length; i++){const w = neighbors[i]if(colors[w] === 'white'){this.dfsVisit(w, colors, callback)}}// 4.访问完节点置黑色colors[vertexes] = 'black'}}

图测试用例

在这里插入图片描述

 const graph = new Graph()// 1.添加顶点const myVertices = ['A', 'B', 'C', 'D', 'E', 'F','G', 'H','I']for(let i = 0; i < myVertices.length; i++){graph.addVertex(myVertices[i])}// 2.添加边graph.addEdge('A', 'B')graph.addEdge('A', 'C')graph.addEdge('A', 'D')graph.addEdge('C', 'D')graph.addEdge('C', 'G')graph.addEdge('D', 'G')graph.addEdge('D', 'H')graph.addEdge('B', 'E')graph.addEdge('B', 'F')graph.addEdge('E', 'I')console.log(graph.toString())// 测试广度优先遍历let result = ''graph.bfs(graph.vertexes[0], function(v){result += v + ' '})console.log(result)// 测试深度优先遍历let deepRsult = ''graph.dfs(graph.vertexes[0], function(v){deepRsult += v + ' '})console.log(deepRsult)

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

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

相关文章

六级仔细阅读

画两到三个词&#xff0c;精准定位 要原文和同义都满足才选 先看题目&#xff0c;在看原文&#xff0c;不要先看选项 做不出答案就继续往下读&#xff0c;读出来了就不用继续读了 分清楚是问为什么还是是什么&#xff0c;是什么看前面&#xff0c;为什么看后面 不知道就优先…

react18【系列实用教程】useState (2024最新版)

类似 vue 的 data 选项 功能 向组件添加响应式变量&#xff0c;当响应式变量变化时&#xff0c;组件的视图UI也会跟着变化【数据驱动视图】 语法 参数为变量的初始值返回值为一个只有两个元素的数组&#xff0c;第一项元素为传入的参数&#xff0c;第二项元素是一个setter 函数…

Rust 的 Warp 库编写的 restful api 参数传递与解析方法

Warp是一个用 Rust 编写的流行的异步 web 框架。在使用 warp 构建 RESTful API 时&#xff0c;可以通过多种方式传递参数到你的处理函数中。 以下是一些常见的方法&#xff0c;说明如何在 warp 中传递参数&#xff1a; 路径参数&#xff1a; 你可以使用 warp::path 和 warp::…

力扣HOT100 - 215. 数组中第K个最大元素

解题思路&#xff1a; 快速选择&#xff0c;目标是找出数组中第 k 小&#xff08;或第 k 大&#xff09;的元素&#xff0c;而不是对整个数组进行排序。 &#xff08;需要和快排进行区分&#xff0c;快排的目的是排序&#xff09; 注意&#xff1a; i l - 1, j r 1; 为什…

Spring Boot集成zookeeper快速入门Demo

1.什么是zookeeper&#xff1f; Zookeeper 是一个开源的分布式协调服务&#xff0c;目前由 Apache 进行维护。Zookeeper 可以用于实现分布式系统中常见的发布/订阅、负载均衡、命令服务、分布式协调/通知、集群管理、Master 选举、分布式锁和分布式队列等功能。它具有以下特性…

大众点评全国店铺基础信息采集-爱车类店铺

2024年5月最新采集大众点评全国(内地)-爱车大类-店铺基础信息&#xff0c;120余万家 爱车类店铺 示例&#xff1a; 店铺id H7hoMM74HIBAREpy 店铺名称 手把手汽车陪练(北京总部) 十分制效果评分 9.2 十分制服务评分 9.2 十分制环境评分 9.2 人均价格 1233 评价数量 514…

学习Java的日子 Day45 HTML常用的标签

Day45 HTML 1.掌握常用的标签 1.1 标题标签 h1-h6 <h1>一级标签</h1> <h2>二级标签</h2> <h3>三级标签</h3> <h4>四级标签</h4> <h5>五级标签</h5> <h6>六级标签</h6> 显示特点&#xff1a; * 文字…

C语言经典例题-13

1.小乐乐走台阶 题目描述: 小乐乐上课需要走n阶台阶&#xff0c;因为他腿比较长&#xff0c;所以每次可以选择走一阶或者走两阶&#xff0c;那么他一共有多少种走法&#xff1f; 输入描述: 输入包含一个整数n (1 ≤ n ≤ 30) 输出描述: 输出一个整数&#xff0c;即小乐乐可以…

MemoryModule - exp - test

文章目录 MemoryModule - exp - test概述笔记测试环境GetModuleFileName不能正常执行GetModuleFileNameWntdll_LdrGetDllFullName猜测原因用LoadLibrary载入的DLL中功能是正常的 gLog可以正常使用内存载入DLL无法支持的功能的折中方法COM操作正常调用方代码接口代码 接口入参测…

基于springboot实现毕业设计系统项目【项目源码+论文说明】

基于springboot实现毕业设计系统演示 摘要 在如今社会上&#xff0c;关于信息上面的处理&#xff0c;没有任何一个企业或者个人会忽视&#xff0c;如何让信息急速传递&#xff0c;并且归档储存查询&#xff0c;采用之前的纸张记录模式已经不符合当前使用要求了。所以&#xff…

绝地求生:盘点宝箱中能开出来的极品皮肤!

最近杜卡迪联名大伙儿不都开箱子出了一堆皮肤吗&#xff1f;很多人搞不清哪些皮肤要留&#xff0c;哪些皮肤可以分。 OK这篇文章稍微推荐几个我认为的高质量可兑换的皮肤&#xff0c;当然个人整理难免有疏漏&#xff0c;欢迎评论区补充。 余波学院黑丝袜 目前游戏里唯一一条显…

力扣 873. 最长的斐波那契子序列的长度 python AC

动态规划做法 class Solution:def lenLongestFibSubseq(self, arr):size len(arr)dp [[2] * size for _ in range(size)]maxv 0for i in range(2, size):for j in range(1, i):d arr[i] - arr[j]l, r 0, j - 1while l < r:mid (l r) // 2if arr[mid] d:l midbreak…

pgbackrest 备份工具使用 postgresql

为啥我会使用pgbackrest进行备份&#xff1f;因为postgresql没有自带的差异备份工具。。。而我们在生产环境上&#xff0c;一般都需要用到差异备份或者增量备份。我们的备份策略基本是&#xff0c;1天1次完整备份&#xff0c;1个小时1次差异备份。如果只需要完整备份&#xff0…

「PHP系列」PHP DOM扩展库/SimpleXML 解析XML文档

文章目录 一、DOM介绍二、DOM扩展库解析XML1. 加载XML文档2. 访问DOM树3. 读取和修改节点数据4. 保存修改后的XML文档5. 注意事项&#xff1a; 三、SimpleXML解析XML1. 加载XML文档2. 访问XML数据3. 修改XML数据4. 保存修改后的XML文档5. 注意事项&#xff1a; 四、相关链接 一…

Linux setserial命令教程:如何配置与查询串口设备(附实例详解和注意事项)

Linux setserial命令介绍 setserial 是一个用于获取和设置Linux串口信息的程序。这些信息包括特定串口使用的I/O端口和IRQ&#xff0c;是否将中断键解释为安全注意键等。 Linux setserial命令适用的Linux版本 setserial命令在大多数Linux发行版中都可以使用&#xff0c;包括…

知识库文档系统源码部署/搭建/上线/运营/售后/更新

一款基于ThinkPHPFastAdmin开发的知识库文档系统&#xff0c;可用于企业工作流程的文档管理&#xff0c;结构化记录沉淀高价值信息&#xff0c;形成完整的知识体系&#xff0c;能够轻松提升知识的流转和传播效率&#xff0c;更好地成就组织和个人。为部门、团队或项目搭建知识库…

SVN 合并到 Git 时有文件大于 100 M 被限制 Push

如果有文件大小大于 100M&#xff0c;GitHub 是会被限制推送到仓库中的&#xff0c;大概率情况会显示下面的错误&#xff1a; remote: Resolving deltas: 100% (3601/3601), done. remote: error: Trace: aea1f450da6f2ef7bfce457c715d0fbb9b0f6d428fdca80233aff34b601ff59b re…

LeetCode 513.找树左下角的值

LeetCode 513.找树左下角的值 1、题目 题目链接&#xff1a;513. 找树左下角的值 给定一个二叉树的 根节点 root&#xff0c;请找出该二叉树的 最底层 最左边 节点的值。 假设二叉树中至少有一个节点。 示例 1: 输入: root [2,1,3] 输出: 1示例 2: 输入: [1,2,3,4,null…

服务端JavaScript(Node.js)与去IO编程:Node.js的事件驱动和非阻塞IO模型,它是如何使JavaScript走向后端的

在Node.js中&#xff0c;JavaScript代码运行在V8引擎上。由于JavaScript是单线程语言&#xff0c;一次只能处理一个事件。为了解决这个问题&#xff0c;Node.js引入了事件驱动模型。每个进行IO操作的函数都是异步的&#xff0c;当这个函数被调用的时候&#xff0c;它不会立即执…

基于单片机的医用辅助器械简析

摘 要&#xff1a;单片机在医用辅助器械中用途广泛&#xff0c;传感装置与单片机控制系统相结合可设计出满足更多需求的医用辅助器械。本文主要探究不同传感装置与单片机结合的优缺点&#xff0c;先从分析医用辅助器械的工作原理入手&#xff0c;说明传感装置的作用&#xff0…