当前位置: 首页 > news >正文

JS实现树形结构、一维数组以及map之间的转换

const treeData=[
{id:1,
name:'中国',
children:[
{id:11,name:'河南省',children:[{id:111,name:'南阳市',children:[{id:1111,name:'淅川县',children:null}]},{id:112,name:'郑州市',children:[{id:1121,name:'中牟县',children:null}]}]
},
{id:22,name:'广东省',children:[{id:221,name:'深圳市',children:[{id:2211,name:'宝安区',children:null},{id:2212,name:'福田区',children:null}]},{id:222,name:'广州市',children:[{id:2221,name:'天河区',children:null},{id:2222,name:'南沙区',children:null}]}]
}]}
]
const listData1=[
{id:1,name:'中国'},
{id:11,name:'河南省',pid:1},
{id:111,name:'南阳市',pid:11},
{id:1111,name:'淅川县',pid:111},
{id:112,name:'郑州市',pid:11},
{id:1121,name:'中牟县',pid:112},
{id:12,name:'广东省',pid:1},
{id:121,name:'深圳市',pid:12},
{id:1211,name:'宝安区',pid:121},
{id:1212,name:'福田区',pid:121},
{id:122,name:'广州市',pid:12},
{id:1221,name:'天河区',pid:122},
{id:1222,name:'南沙区',pid:122},
]

1、一维数组转树形结构

1.1、递归

//一维数组转树形结构
function listToTree(list){const tree=[]for(const node of list){//如果是父节点if(!node.pid){let p={...node}p.children=getChildren(p.id,list)tree.push(p)}}return tree
}
function getChildren(id,list){const children=[]//遍历数组的每一个元素,如果找到元素的父元素节点等于当前节点,则向children中添加该元素for(const node of list){if(node.pid===id){children.push(node)}}//遍历每一个孩子节点,递归寻找孩子的孩子节点,如果存在children,则向node的children中添加for(const node of children){const children=getChildren(node.id,list)if(children.length){node.children=children}}return children
}

demo:

console.log(listToTree(listData))

打印后的结果和treeData一致。

1.2、双层循环

// 双层循环:找出每一个元素的父节点,向每一个父节点增加children属性
function listToTree2(list){list.forEach(child=>{const pid=child.pid//遍历子节点,然后遍历每一个list节点,从中找出父节点,向父节点增加孩子元素if(pid){list.forEach(parent=>{if(parent.id===pid){//如果找到的父节点还没有孩子,会默认为空数组,否则为原来的子节点数组                    parent.children=parent.children||[]parent.children.push(child)}})}})
}

结果同1.1

1.3、使用map

//Map
function listToListMap(list){const [map,treeData]=[{},[]]//将map转为以id为key,索引为value的对象//将数组中每个元素的children初始化为空数组for(let i=0;i<list.length;i++){map[list[i].id]=i;list[i].children=[]}console.log(map)for(let i=0;i<list.length;i++){const node=list[i]//如果是子元素并且子元素的父节点存在在list中,则找到父元素并向父元素的children中加入子元素if(node.pid&&list[map[node.pid]]){list[map[node.pid]].children.push(node)}else{//说明不是子元素,是父元素直接放入treeData中treeData.push(node)}}return treeData
}

2、tree转list

树形结构转数组涉及到树的遍历,树的遍历分为深度遍历(前中后序)和广度遍历。

2.1、广度遍历

const treeData3=[
{id:1,
name:'中国',
children:[
{id:11,name:'河南省',children:[{id:111,name:'南阳市',pid:11,children:[{id:1111,name:'淅川县',children:null,pid:111,}]},{id:112,name:'郑州市',pid:11,children:[{id:1121,pid:112,name:'中牟县',children:null}]}]
},
{id:22,name:'广东省',children:[{id:221,pid:22,name:'深圳市',children:[{id:2211,pid:221,name:'宝安区',children:null},{id:2212,pid:221,name:'福田区',children:null}]},{id:222,pid:22,name:'广州市',children:[{id:2221,pid:222,name:'天河区',children:null},{id:2222,pid:222,name:'南沙区',children:null}]}]
}]}
]
//广度遍历(一层一层遍历)
function treeToList(treeData){const list=[]const queue=[...treeData]while(queue.length){//取队头元素         const node=queue.shift()const children=node.children//将队头元素的孩子依次放入队列中便于后序遍历if(children){queue.push(...children)}//放入元素节点list.push(node)}return list
}
console.log(treeToList(treeData3))

打印结果同1中的listData

2.2、深度遍历

//深度遍历(采用栈)
function treeToList2(tree){const list=[]const stack=[...tree]while(stack.length){const node=stack.pop()//如果出栈的节点有孩子元素,那么将出栈元素的所有孩子元素都放入栈中,便于后续遍历.const children=node.childrenif(children){stack.push(...children)}list.push(node)}return list
}

3、list转Map(map是以父节点id为key,所有子节点作为数组为value的数据结构)

const listData4=[
{id:1,name:'中国'},//0
{id:11,name:'河南省',pid:1},//1
{id:111,name:'南阳市',pid:11},//2
{id:1111,name:'淅川县',pid:111},//3
{id:112,name:'郑州市',pid:11},//4
{id:1121,name:'中牟县',pid:112},//5
{id:12,name:'广东省',pid:1},//6
{id:121,name:'深圳市',pid:12},//7
{id:1211,name:'宝安区',pid:121},//8
{id:1212,name:'福田区',pid:121},//9
{id:122,name:'广州市',pid:12},//10
{id:1221,name:'天河区',pid:122},//11
{id:1222,name:'南沙区',pid:122},//12
]
// 将列表数据转为以父节点id为key,子节点为value的map
function listToMap(list){const map={}list.forEach(item=>{for(let i=0;i<list.length;i++){//如果外层循环元素的id等于内层循环元素的pid,说明内层元素是外层元素的子元素,则向map的value中添加该内层元素.if(list[i].pid===item.id){map[item.id]=map[item.id]||[]map[item.id].push(list[i])}}})return map
}
console.log(listToMap(listData4))

 

相关文章:

JS实现树形结构、一维数组以及map之间的转换

const treeData[ {id:1, name:中国, children:[ {id:11,name:河南省,children:[{id:111,name:南阳市,children:[{id:1111,name:淅川县,children:null}]},{id:112,name:郑州市,children:[{id:1121,name:中牟县,children:null}]}] }, {id:22,name:广东省,children:[{id:221,name:…...

Vue中自定义.js变量

1、定义.js文件 order.js文件内容&#xff1a; // 订单是否报账 const EXPENESS_STATUS_NO0; const EXPENESS_STATUS_YES1; // 状态 0-未发货 1-发货 2-确认收获 const STATUS_NO0; const STATUS_SEND1; const STATUS_DELIVERY2; // 如何不加这个&#xff0c;vue中引…...

基于深度信念神经网络+长短期神经网络的降雨量预测,基于dbn-lstm的降雨量预测,dbn原理,lstm原理

目录 背影 DBN神经网络的原理 DBN神经网络的定义 受限玻尔兹曼机(RBM) LSTM原理 DBN-LSTM的降雨量预测 基本结构 主要参数 数据 MATALB代码 结果图 展望 背影 DBN是一种深度学习神经网络,拥有提取特征,非监督学习的能力,通过dbn进行无监督学习提取特征,然后长短期神经…...

SyntaxError: Cannot use import statement outside a module

node环境运行报错&#xff1a; 解决步骤&#xff1a; 1. npm init -y 2. 在 package.json 文件中加入一条&#xff1a;"type": "module", 3. 保存后再执行即可 附&#xff1a;最好是不要在node用import&#xff0c;否则需要上次配置 建议1&#xff1a;用re…...

为什么要做数据可视化系统

数据可视化系统在当今数字时代发挥着重要的作用&#xff0c;成为许多组织和企业的不可或缺的工具。随着信息爆炸式增长和数据处理的需求不断增加&#xff0c;数据可视化系统帮助人们更好地理解和分析数据&#xff0c;为决策提供重要支持。数聚股份将详细介绍为什么要做数据可视…...

Java项目作业~ 通过html+Servlet+MyBatis,完成站点信息的添加功能

需求&#xff1a; 通过htmlServletMyBatis&#xff0c;完成站点信息的添加功能。 以下是站点表的建表语句&#xff1a; CREATE TABLE websites (id int(11) NOT NULL AUTO_INCREMENT,name char(20) NOT NULL DEFAULT COMMENT 站点名称,url varchar(255) NOT NULL DEFAULT ,…...

基于 Arduino 编写 ESP32 BLE Server 例程

测试代码如下&#xff1a; 支持 BLE 连接支持 BLE 数据传输 #include <BLEDevice.h> #include <BLEServer.h> #include <BLEUtils.h>namespace BLEServerDemo {BLEServer *pServer nullptr; BLEService *pService nullptr; BLECharacteristic *pCharacte…...

Mac环境变量配置

export HOMEBREW_NO_AUTO_UPDATEtrue关闭Homebrew自动更新&#xff0c;因为每次安装软件都要自动更新&#xff0c;特别慢export JAVA_HOME/Library/Java/JavaVirtualMachines/jdk1.8.0_271.jdk/Contents/Home配置JAVA_HOMEexport ANDROID_HOME/Users/fanpaopao/Library/Android…...

使用FTP文件传输协议的潜在风险

数据&#xff08;事实&#xff0c;数字&#xff0c;价值&#xff09;是当今业务运行的核心要素。但是&#xff0c;如果数据没有得到有效的存储和传输&#xff0c;它们就会成为阻碍业务发展的障碍。如果企业不能及时地把数据送到合适的地方&#xff0c;就会造成严重的经济损失。…...

Jtti:windows虚拟内存最小值太低如何解决

当Windows虚拟内存的最小值设置过低时&#xff0c;可能会导致系统性能下降、应用程序崩溃甚至系统不稳定。解决方法包括&#xff1a; 调整虚拟内存设置&#xff1a; 可以通过以下步骤调整虚拟内存的设置&#xff1a; 右键点击“此电脑”或“计算机”&#xff0c;选择“属性”。…...

基于微服务+Java+Spring Cloud +Vue+UniApp +MySql实现的智慧工地云平台源码

基于微服务JavaSpring Cloud VueUniApp MySql开发的智慧工地云平台源码 智慧工地概念&#xff1a; 智慧工地就是互联网建筑工地&#xff0c;是将互联网的理念和技术引入建筑工地&#xff0c;然后以物联网、移动互联网技术为基础&#xff0c;充分应用BIM、大数据、人工智能、移…...

Unity框架学习--4 Mono管理器

作用&#xff1a;使不继承MonoBehaviour的类能够开启协程&#xff0c;并且可以使用FixedUpdate、Update、LateUpdate进行每帧更新。 原理&#xff1a; 1、在场景中创建一个继承MonoBehaviour的“执行者”脚本&#xff0c;这个脚本就专门用来开启协程和监听帧更新。 2、Mono管理…...

Unity zSpace 开发

文章目录 1.下载 zSpace 开发环境1.1 zCore Unity Package1.2 zView Unity Package 2. 导入工程3. 发布设置4.功能实现4.1 用触控笔来实现对模型的拖拽&#xff1a; 5. 后续更新 1.下载 zSpace 开发环境 官网地址 1.1 zCore Unity Package zSpace 开发核心必须 1.2 zView …...

SQL注入是什么?如何防范?

什么是SQL注入&#xff1f; SQL注入&#xff08;SQLi&#xff09;是一种注入攻击&#xff0c;可以执行恶意SQL语句。它通过将任意SQL代码插入数据库查询&#xff0c;使攻击者能够完全控制Web应用程序后面的数据库服务器。攻击者可以使用SQL注入漏洞绕过应用程序安全措施&#…...

Spring kafka源码分析——消息是如何消费的

文章目录 概要端点注册创建监听容器启动监听容器消息拉取与消费小结 概要 本文主要从Spring Kafka的源码来分析&#xff0c;消费端消费流程&#xff1b;从spring容器启动到消息被拉取下来&#xff0c;再到执行客户端自定义的消费逻辑&#xff0c;大致概括为以下4个部分&#x…...

汽车电子的发展对国产32位MCU的影响

32位MCU是目前产品市场的主流&#xff0c;尤其是在汽车电子发展起来后&#xff0c;32位MCU在市场的比重迅速增涨&#xff0c;国内32位MCU厂商抓住风口&#xff0c;推出一系列汽车电子芯片从而稳定国内市场。如芯海的CS32F030系列就是主要应用汽车电子市场的32位MCU。 根据市场…...

Vue 目录结构 vite 项目

Vue3 项目常用的目录结构和每个文件的作用【通过 vite 创建的项目】 vite目录结构&#xff1a; dist // 打包后生成的文件目录 node_modules // 环境依赖 public // 公共资源目录 favicon.ico …...

TB/TM-商品详情原数据(APP)

一、接口参数说明&#xff1a; item_get_app-获得TB/TMapp商品详情原数据&#xff0c;点击更多API调试&#xff0c;请移步注册API账号点击获取测试key和secret 公共参数 请求地址: https://api-gw.onebound.cn/taobao/item_get_app 名称类型必须描述keyString是调用key&…...

小米发布会:雷军成长故事与创新壮举,AI大模型技术引领未来,雷军探索之路之从创业波折到小米AI领航,成就高端化传奇!

&#x1f337;&#x1f341; 博主猫头虎 带您 Go to New World.✨&#x1f341; &#x1f984; 博客首页——猫头虎的博客&#x1f390; &#x1f433;《面试题大全专栏》 文章图文并茂&#x1f995;生动形象&#x1f996;简单易学&#xff01;欢迎大家来踩踩~&#x1f33a; &a…...

春秋云镜 CVE-2021-41947

春秋云镜 CVE-2021-41947 Subrion CMS v4.2.1 存在sql注入 靶标介绍 Subrion CMS v4.2.1 存在sql注入。 启动场景 漏洞利用 exp http://localhost/panel/visual-mode.json?getaccess&typeblocks UNION ALL SELECT username, password FROM sbr421_members -- -&o…...

应用升级/灾备测试时使用guarantee 闪回点迅速回退

1.场景 应用要升级,当升级失败时,数据库回退到升级前. 要测试系统,测试完成后,数据库要回退到测试前。 相对于RMAN恢复需要很长时间&#xff0c; 数据库闪回只需要几分钟。 2.技术实现 数据库设置 2个db_recovery参数 创建guarantee闪回点&#xff0c;不需要开启数据库闪回。…...

MongoDB学习和应用(高效的非关系型数据库)

一丶 MongoDB简介 对于社交类软件的功能&#xff0c;我们需要对它的功能特点进行分析&#xff1a; 数据量会随着用户数增大而增大读多写少价值较低非好友看不到其动态信息地理位置的查询… 针对以上特点进行分析各大存储工具&#xff1a; mysql&#xff1a;关系型数据库&am…...

ESP32 I2S音频总线学习笔记(四): INMP441采集音频并实时播放

简介 前面两期文章我们介绍了I2S的读取和写入&#xff0c;一个是通过INMP441麦克风模块采集音频&#xff0c;一个是通过PCM5102A模块播放音频&#xff0c;那如果我们将两者结合起来&#xff0c;将麦克风采集到的音频通过PCM5102A播放&#xff0c;是不是就可以做一个扩音器了呢…...

uniapp微信小程序视频实时流+pc端预览方案

方案类型技术实现是否免费优点缺点适用场景延迟范围开发复杂度​WebSocket图片帧​定时拍照Base64传输✅ 完全免费无需服务器 纯前端实现高延迟高流量 帧率极低个人demo测试 超低频监控500ms-2s⭐⭐​RTMP推流​TRTC/即构SDK推流❌ 付费方案 &#xff08;部分有免费额度&#x…...

Map相关知识

数据结构 二叉树 二叉树&#xff0c;顾名思义&#xff0c;每个节点最多有两个“叉”&#xff0c;也就是两个子节点&#xff0c;分别是左子 节点和右子节点。不过&#xff0c;二叉树并不要求每个节点都有两个子节点&#xff0c;有的节点只 有左子节点&#xff0c;有的节点只有…...

分布式增量爬虫实现方案

之前我们在讨论的是分布式爬虫如何实现增量爬取。增量爬虫的目标是只爬取新产生或发生变化的页面&#xff0c;避免重复抓取&#xff0c;以节省资源和时间。 在分布式环境下&#xff0c;增量爬虫的实现需要考虑多个爬虫节点之间的协调和去重。 另一种思路&#xff1a;将增量判…...

算法岗面试经验分享-大模型篇

文章目录 A 基础语言模型A.1 TransformerA.2 Bert B 大语言模型结构B.1 GPTB.2 LLamaB.3 ChatGLMB.4 Qwen C 大语言模型微调C.1 Fine-tuningC.2 Adapter-tuningC.3 Prefix-tuningC.4 P-tuningC.5 LoRA A 基础语言模型 A.1 Transformer &#xff08;1&#xff09;资源 论文&a…...

Java求职者面试指南:计算机基础与源码原理深度解析

Java求职者面试指南&#xff1a;计算机基础与源码原理深度解析 第一轮提问&#xff1a;基础概念问题 1. 请解释什么是进程和线程的区别&#xff1f; 面试官&#xff1a;进程是程序的一次执行过程&#xff0c;是系统进行资源分配和调度的基本单位&#xff1b;而线程是进程中的…...

基于Springboot+Vue的办公管理系统

角色&#xff1a; 管理员、员工 技术&#xff1a; 后端: SpringBoot, Vue2, MySQL, Mybatis-Plus 前端: Vue2, Element-UI, Axios, Echarts, Vue-Router 核心功能&#xff1a; 该办公管理系统是一个综合性的企业内部管理平台&#xff0c;旨在提升企业运营效率和员工管理水…...

C# 表达式和运算符(求值顺序)

求值顺序 表达式可以由许多嵌套的子表达式构成。子表达式的求值顺序可以使表达式的最终值发生 变化。 例如&#xff0c;已知表达式3*52&#xff0c;依照子表达式的求值顺序&#xff0c;有两种可能的结果&#xff0c;如图9-3所示。 如果乘法先执行&#xff0c;结果是17。如果5…...