【Java用法】Hutool树结构工具-TreeUtil快速构建树形结构的两种方式 + 数据排序

Hutool树结构工具-TreeUtil快速构建树形结构的两种方式 + 数据排序

  • 一、业务场景
  • 二、Hutool官网树结构工具
    • 2.1 介绍
    • 2.2 使用
      • 2.2.1 定义结构
      • 2.2.2 构建Tree
      • 2.2.3 自定义字段名
    • 2.3 说明
  • 三、具体的使用场景
    • 3.1 实现的效果
    • 3.2 业务代码
    • 3.3 实现自定义字段的排序
  • 四、踩过的坑
    • 4.1 坑1:weight权重属性 类型异常
    • 4.2 坑2:weight权重属性 字符串只能根据首字母排序

一、业务场景

Springboot + vue 开发;

想实现树结构业务,并在树结构节点有业务功能,比如根据树结构节点排序、节点的状态显示等功能。

在开发过程中,必定会遇到树形结构的数据,一般都是后端直接从库里查询出来然后自定义方法去封装成树形树形返回给前端。这里就会用到递归、封装再返回,非常麻烦。后来发现 HutoolUtil 中有个工具类 TreeUtil 可以完成本次项目的需求,非常便捷,使用方式很简单,本次就使用它来实现。

二、Hutool官网树结构工具

如果想查询Hutool官网最新的树结构工具,请各位看官移步至传送门:官网树结构工具-TreeUtil。

以下是当时使用此 TreeUtil 时的官网介绍。

2.1 介绍

考虑到菜单等需求的普遍性,有用户提交了一个扩展性极好的树状结构实现。这种树状结构可以根据配置文件灵活的定义节点之间的关系,也能很好的兼容关系数据库中数据。实现 关系型数据库数据 <-> Tree <-> JSON 树状结构中最大的问题就是关系问题,在数据库中,每条数据通过某个字段关联自己的父节点,每个业务中这个字段的名字都不同,如何解决这个问题呢?

PR的提供者提供了一种解决思路:自定义字段名,节点不再是一个bean,而是一个map,实现灵活的字段名定义。

2.2 使用

2.2.1 定义结构

我们假设要构建一个菜单,可以实现系统管理和店铺管理,菜单的样子如下:

系统管理
|- 用户管理
|- 添加用户
店铺管理
|- 商品管理
|- 添加商品

那这种结构如何保存在数据库中呢?一般是这样的:

在这里插入图片描述

2.2.2 构建Tree

// 构建node列表
List<TreeNode<String>> nodeList = CollUtil.newArrayList();

nodeList.add(new TreeNode<>("1", "0", "系统管理", 5));
nodeList.add(new TreeNode<>("11", "1", "用户管理", 222222));
nodeList.add(new TreeNode<>("111", "11", "用户添加", 0));
nodeList.add(new TreeNode<>("2", "0", "店铺管理", 1));
nodeList.add(new TreeNode<>("21", "2", "商品管理", 44));
nodeList.add(new TreeNode<>("221", "2", "商品管理2", 2));

TreeNode表示一个抽象的节点,也表示数据库中一行数据。 如果有其它数据,可以调用setExtra添加扩展字段。

// 0表示最顶层的id是0
List<Tree<String>> treeList = TreeUtil.build(nodeList, "0");

因为两个Tree是平级的,再没有上层节点,因此为List。

2.2.3 自定义字段名

//配置
TreeNodeConfig treeNodeConfig = new TreeNodeConfig();
// 自定义属性名 都要默认值的
treeNodeConfig.setWeightKey("order");
treeNodeConfig.setIdKey("rid");
// 最大递归深度
treeNodeConfig.setDeep(3);

//转换器
List<Tree<String>> treeNodes = TreeUtil.build(nodeList, "0", treeNodeConfig,
        (treeNode, tree) -> {
            tree.setId(treeNode.getId());
            tree.setParentId(treeNode.getParentId());
            tree.setWeight(treeNode.getWeight());
            tree.setName(treeNode.getName());
            // 扩展属性 ...
            tree.putExtra("extraField", 666);
            tree.putExtra("other", new Object());
        });

通过TreeNodeConfig我们可以自定义节点的名称、关系节点id名称,这样就可以和不同的数据库做对应。

2.3 说明

官网上描述的是最通用和最简单的使用方法,但是在实际开发中,我们的业务场景都会比实际的复杂很多,所以结合业务场景实现此功能。

三、具体的使用场景

3.1 实现的效果

在这里插入图片描述

3.2 业务代码

在这里插入图片描述

3.3 实现自定义字段的排序

使用官网推荐的方法排序

TreeNodeConfig treeNodeConfig = new TreeNodeConfig();
// 自定义属性名 都要默认值的
treeNodeConfig.setWeightKey("order");

然后在转换器中取出此自定义的排序字段时,无论怎么配置和设置都是无法使用自定义的字段。

在网上搜索的自定义方法都是与官网上一样,通过 TreeNodeConfig 配置类设置,然后在转换器 treeNode 类中获取。在我所使用的项目中始终不生效。所以只能靠自己解决了。

通过自己的摸索和研究,如3.2中的代码通过拓展字段可以实现。

然后在转换器中,通过拓展字段把自定义的排序字段取出然后再赋值给 Tree 类中的 weight 属性即可。

四、踩过的坑

4.1 坑1:weight权重属性 类型异常

官网中的weight权重属性不能使用 int 类型的字段,项目启动正常,调用接口时会报类型转换异常错误。

4.2 坑2:weight权重属性 字符串只能根据首字母排序

如果此字段设置为字符串类型的排序字段时,TreeUtil 只会根据首字母排序,限制了我们使用的情况,所以此种情况也不符合我们的期望。

本文完结!

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

中伟视界:皮带跑偏、异物检测AI算法除了矿山行业应用,还能在钢铁、火电、港口等行业中使用吗?

随着工业化的发展&#xff0c;皮带输送机已经成为各行业中不可或缺的重要设备&#xff0c;但是在使用过程中&#xff0c;由于各种原因&#xff0c;皮带常常出现跑偏问题&#xff0c;给生产运营带来了诸多困扰。不仅仅是矿山行业&#xff0c;钢铁、火电、港口等行业也都面临着皮…

英文论文查重复率网址

大家好&#xff0c;今天来聊聊英文论文查重复率网址&#xff0c;希望能给大家提供一点参考。 以下是针对论文重复率高的情况&#xff0c;提供一些修改建议和技巧&#xff1a; 英文论文查重复率网址 在撰写英文论文时&#xff0c;查重是确保论文原创性和质量的重要环节快码论文…

LeetCode Hot100 131.分割回文串

题目&#xff1a; 给你一个字符串 s&#xff0c;请你将 s 分割成一些子串&#xff0c;使每个子串都是 回文串 。返回 s 所有可能的分割方案。 回文串 是正着读和反着读都一样的字符串。 方法&#xff1a;灵神-子集型回溯 假设每对相邻字符之间有个逗号&#xff0c;那么就看…

windows11 windows 11 (win11 win 11) 怎么安装 Python3 ? numpy? sounddevice? 声音信号处理库?

首先确认要安装的 sounddevice 库&#xff0c;链接&#xff1a;https://python-sounddevice.readthedocs.io/en/0.4.6/ 根据文档&#xff0c;可知最新的 sounddevice 版本是 0.4.6 进入安装页面查看&#xff0c;发现 Newest sounddevice 可以使用 pip 安装&#xff0c;如下图…

AGM离线下载器使用说明

AGM专用离线下载器示意图&#xff1a; 供电方式&#xff1a; 通过 USB 接口给下载器供电&#xff0c;跳线 JP 断开。如果客户 PCB 的 JTAG 口不能提供 3.3V 电源&#xff0c;或仅需烧写下载器&#xff0c;尚未连接用户 PCB 时&#xff0c;采用此种方式供电。 或者&#xff1a…

私域运营:12个朋友圈经营模板

做私域运营的各位&#xff0c;想必大家都会烦恼朋友圈要发什么才能保证最高效吧&#xff01; 首先&#xff0c;我们需要明确&#xff0c;朋友圈是什么&#xff1f; 朋友圈是我们打造信任感的地方&#xff0c;也是我们的信息能够及时触达用户的重要渠道。很多人都有一个习惯&a…

线性代数基础【1】行列式

第一节 行列式的基本概念和性质 一、基本概念 ①逆序 1,2和2,1是一对逆序 ②逆序数 1,2,3,5,4的逆序数为1;1,3,2,5,4逆序数为4; ③行列式 ④余子数和代数余子数 行列式挖掉一个数(例如aij),将原行列式去掉i行j列的行列式M,则M为余子数,代数余子数记为Aij,如果(ij)为偶数…

leaflet:经纬度坐标转为地址,点击鼠标显示地址信息(137)

第137个 点击查看专栏目录 本示例的目的是介绍演示如何在vue+leaflet中将经纬度坐标转化为地址,点击鼠标显示某地的地址信息 。主要利用mapbox的api将坐标转化为地址,然后在固定的位置显示出来。 直接复制下面的 vue+leaflet源代码,操作2分钟即可运行实现效果 文章目录 示…

既然UDP更快,为啥这么多年一直用TCP ?

你们好啊&#xff0c;我是老杨。 有点基本技术常识的粉丝朋友都知道&#xff0c;UDP肯定是比TCP快的。 很多人对TCP和UDP的了解很浅&#xff0c;直到自己真的经历了一些通信项目之后&#xff0c;你才会愿意根据实际情况埋头苦学&#xff0c;企图“速成”一下。 要是问你为什…

复杂gRPC之go调用go

1. 复杂的gRPC调用 我们使用了一个较为复杂的proto文件&#xff0c;这个文件的功能主要是用来定位的&#xff0c;详细内容可以看代码中的注解 syntax "proto3"; //指定生成的所属的package&#xff0c;方便调用 option go_package "./"; package route…

KaiwuDB 通过中国信通院“可信数据库”性能与稳定性评测

11月29日&#xff0c;中国信通院 2023 年下半年“可信数据库”评估评测结果正式发布&#xff0c;由 KaiwuDB研发的开务数据库系统 KaiwuDB V2.0 达到信通院时序数据库性能、稳定性测试标准。 至此&#xff0c;KaiwuDB已完成时序数据库基础能力、性能、稳定性全项评测&#xff…

Python Tacacs故障诊断记录

背景&#xff1a;客户现场说我们的设备在3A鉴权时失败&#xff0c;没有认证成功 第一步&#xff0c;先看下我们log 没有明显的错误记录&#xff0c;貌似认证成功了但是确提示认证失败&#xff0c;有点迷 第二步&#xff0c;家里搭建和现场一致的环境&#xff0c;模拟登录发现是…

《文存阅刊》期刊发表简介

《文存阅刊》以“深研文化创新&#xff0c;崇尚科学真理&#xff0c;坚持双百方针&#xff0c;打造学术精品”为办刊宗旨&#xff0c;涵盖艺术、文学、社科等多项内容&#xff0c;适应了文化市场需求&#xff0c;很好的回应了广大文化理论工作者的关切&#xff0c;为下一步打造…

cuda lib 线程安全的要义

1, 概述 cuda lib 线程安全的几个多线程的情景&#xff1a; 单卡多线程&#xff1b; 多卡多线程-每卡单线程&#xff1b; 多卡多线程-每卡多线程&#xff1b; 需要考虑的问题&#xff1a; 每个 cublasHandle_t 只能有一个stream么&#xff1f; 每个cusolverHandle_t 只能有一…

DTS认证

一、什么叫DTS DTS 是“Digital Theatre System“的缩写&#xff0c;是”数字化影院系统“的意思。是一种音频格式&#xff0c;从技术上讲&#xff0c;把音效数据存储到另外的CD-ROM中&#xff0c;使其与影像数据同步。这样不但空间得到增加&#xff0c;而且数据流量也可以相对…

如何运用gpt改写出高质量的文章 (1)

大家好&#xff0c;今天来聊聊如何运用gpt改写出高质量的文章 (1)&#xff0c;希望能给大家提供一点参考。 以下是针对论文重复率高的情况&#xff0c;提供一些修改建议和技巧&#xff1a; 如何运用GPT改写出高质量的文章 一、引言 随着人工智能技术的飞速发展&#xff0c;自然…

HHDESK右键管理简介

在HHDESK管理文件&#xff0c;除了基本的打开、删除、复制、粘贴、重命名外&#xff0c;还有多种便捷编辑方式。 可以分别以下列模式打开文档&#xff1a; 文本模式即是以文本编辑器打开文档。 1 二进制模式 可进行二进制编辑。 2 JSON模式 可对JSON文件进行直观的解析…

b样条原理与测试

为了保留贝塞尔曲线的优点&#xff0c;同时克服贝塞尔曲线的缺点&#xff0c;b样条在贝塞尔曲线上发展而来&#xff0c;首先来看贝塞尔曲线的定义&#xff1a; 对于贝塞尔中的基函数而言&#xff0c;是确定的&#xff0c;全局唯一的&#xff0c;这导致了如果控制点发生变换将会…

软件测试--selenium安装使用

安装selenium不少人使用pip命令来安装selenium&#xff0c;辛辛苦苦安装完之后&#xff0c;还是不能使用。所以我们可以是直接使用编译器&#xff0c;pycharm直接安装selenium扩展包。 file中点击settings 在Settings中点击Project Interpreter,点击加号就可以安装各种需要的扩…

11.30BST理解,AVL树操作,定义;快速幂,二分求矩阵幂(未完)

完全二叉树结点的度可能有1&#xff0c;满二叉树的度只能为0或2 BST构建 BST是左孩子都比根节点小&#xff0c;右孩子都比根节点大 二叉搜索树的插入&#xff0c;删除&#xff0c;调整 平衡树理解 任何一个平衡二叉树&#xff0c;它的中序遍历都是一样的&#xff0c;都是有…