Python 无限级分类树状结构生成算法的实现


Posted in Python onJanuary 21, 2021

后端研发的同学对无限级分类肯定映像深刻,当初花了不少时间吧?

无限级分类树状结构的应用场景很多,例如后端研发需要把用户相关权限读取出来并生成树状结构,前端研发拿到权限树之后可以按照结构展示用户有权限访问的栏目;再例如网页上的栏目分级:

Python 无限级分类树状结构生成算法的实现

作者在初次接触树状结构生成需求的时候,也是挠头,后来找到了一个代码少且清晰易懂的生成算法:递归。

首先,确保数据库中存储的类别信息如下:

[
 {"id": 1, "name": '电器', "parent": 0},
 {"id": 2, "name": '水果', "parent": 0},
 {"id": 3, "name": '家用电器', "parent": 1},
 {"id": 4, "name": '电吹风', "parent": 3},
 {"id": 5, "name": '电风扇', "parent": 3},
 {"id": 6, "name": '台灯', "parent": 3},
 {"id": 7, "name": '商用电器', "parent": 1},
 {"id": 8, "name": '大型电热锅', "parent": 7},
]

字段 parent 记录的是此条目的父编号,例如电吹风的父编号是 3,即电吹风属于家用电器,而家用电器的父编号是 1,即家用电器属于电器类产品。电吹风条目跟电器条目并无直接的标识进行关联,但需要用树状结构来表明 电器 <- 家用电器 <- 电吹风 的关系。

通过 parent 寻找父编号,并建立关联关系的操作实际上是循环往复的,直到找完所有的结点,这跟递归算法非常契合,很轻松便能写出对应的递归代码:

def generate_tree(source, parent):
 tree = []
 for item in source:
 if item["parent"] == parent:
 item["child"] = generate_tree(source, item["id"])
 tree.append(item)
 return tree

只需要将数据库中存储的信息传递给 generate_tree 函数即可。这段递归代码在往复循环的过程中通过 parent 来寻找子结点,找到子结点后将其添加到树中。完整代码如下:

import json
def generate_tree(source, parent):
 tree = []
 for item in source:
 if item["parent"] == parent:
 item["child"] = generate_tree(source, item["id"])
 tree.append(item)
 return tree
if __name__ == '__main__':
 permission_source = [
 {"id": 1, "name": '电器', "parent": 0},
 {"id": 2, "name": '水果', "parent": 0},
 {"id": 3, "name": '家用电器', "parent": 1},
 {"id": 4, "name": '电吹风', "parent": 2},
 {"id": 5, "name": '电风扇', "parent": 3},
 {"id": 6, "name": '台灯', "parent": 3},
 {"id": 7, "name": '商用电器', "parent": 1},
 {"id": 8, "name": '大型电热锅', "parent": 7},
 ]
 permission_tree = generate_tree(permission_source, 0)
 print(json.dumps(permission_tree, ensure_ascii=False))

你试试运行一下,看看结构是否符合预期。

使用缓存优化算法

递归算法中有很多重复的计算,这些计算不仅占用额外资源,还会降低函数执行效率,因此需要对递归进行优化。这里选用缓存优化法提升函数执行效率。

基本思路是每次找到结点关系后将此条目的编号添加到一个列表中缓存起来,代表此条目已找到结点关系。当往复循环执行函数时再次遇到此条目可以跳过。代码改动很简单,增加一个缓存列表和控制流语句即可:

def generate_tree(source, parent, cache=[]):
 tree = []
 for item in source:
 if item["id"] in cache:
 continue
 if item["parent"] == parent:
 cache.append(item["id"])
 item["child"] = generate_tree(source, item["id"], cache)
 tree.append(item)
 return tree

至此,无限级分类树状结构生成算法完成。你学会了吗?

到此这篇关于Python 无限级分类树状结构生成算法的实现的文章就介绍到这了,更多相关Python 无限级分类树状结构内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Python 相关文章推荐
python实现基本进制转换的方法
Jul 11 Python
使用Python从有道词典网页获取单词翻译
Jul 03 Python
完美解决python遍历删除字典里值为空的元素报错问题
Sep 11 Python
Python实现的字典值比较功能示例
Jan 08 Python
对TensorFlow的assign赋值用法详解
Jul 30 Python
详解Python中的测试工具
Jun 09 Python
对pyqt5多线程正确的开启姿势详解
Jun 14 Python
Python的numpy库下的几个小函数的用法(小结)
Jul 12 Python
使用python和pygame制作挡板弹球游戏
Dec 03 Python
基于Tensorflow使用CPU而不用GPU问题的解决
Feb 07 Python
MxNet预训练模型到Pytorch模型的转换方式
May 25 Python
Python中的 enumerate和zip详情
May 30 Python
python 制作网站筛选工具(附源码)
Jan 21 #Python
python使用scapy模块实现ping扫描的过程详解
Jan 21 #Python
Python 中如何使用 virtualenv 管理虚拟环境
Jan 21 #Python
python使用scapy模块实现ARP扫描的过程
Jan 21 #Python
Python3利用scapy局域网实现自动多线程arp扫描功能
Jan 21 #Python
Pandas直接读取sql脚本的方法
Jan 21 #Python
python asyncio 协程库的使用
Jan 21 #Python
You might like
PHP VS ASP
2006/10/09 PHP
thinkphp文件引用与分支结构用法实例
2014/11/26 PHP
php简单实现发送带附件的邮件
2015/06/10 PHP
PHP错误和异常处理功能模块示例
2016/11/12 PHP
JavaScript 以对象为索引的关联数组
2010/05/19 Javascript
一个JQuery操作Table的代码分享
2012/03/30 Javascript
javascript中的if语句使用介绍
2013/11/20 Javascript
Javascript 鼠标移动上去 滑块跟随效果代码分享
2013/11/23 Javascript
js实现发送验证码后的倒计时功能
2015/05/28 Javascript
JavaScript中Number.MIN_VALUE属性的使用示例
2015/06/04 Javascript
基于jQuery+JSON的省市二三级联动效果
2015/06/05 Javascript
Three.js学习之网格
2016/08/10 Javascript
深入浅析Vue组件开发
2016/11/25 Javascript
对Vue beforeRouteEnter 的next执行时机详解
2018/08/25 Javascript
vue 路由缓存 路由嵌套 路由守卫 监听物理返回操作
2020/08/06 Javascript
Postman参数化实现过程及原理解析
2020/08/13 Javascript
JS继承实现方法及优缺点详解
2020/09/02 Javascript
[01:07:57]DOTA2-DPC中国联赛 正赛 Ehome vs Magma BO3 第二场 1月19日
2021/03/11 DOTA
Python作用域用法实例详解
2016/03/15 Python
分享给Python新手们的几道简单练习题
2017/09/21 Python
彻底搞懂Python字符编码
2018/01/23 Python
python贪婪匹配以及多行匹配的实例讲解
2018/04/19 Python
pycharm 在windows上编辑代码用linux执行配置的方法
2018/10/27 Python
Python函数返回不定数量的值方法
2019/01/22 Python
django多个APP的urls设置方法(views重复问题解决)
2019/07/19 Python
PyTorch实现AlexNet示例
2020/01/14 Python
解决python父线程关闭后子线程不关闭问题
2020/04/25 Python
python上selenium的弹框操作实现
2020/07/13 Python
巴黎一票通:The Paris Pass
2018/02/10 全球购物
辩论赛主持词
2014/03/18 职场文书
战略合作协议书范本
2014/04/18 职场文书
教师党员群众路线教育实践活动心得体会
2014/11/04 职场文书
会议简报格式范文
2015/07/20 职场文书
青年教师听课心得体会
2016/01/15 职场文书
Java中CyclicBarrier和CountDownLatch的用法与区别
2021/08/23 Java/Android
python_tkinter事件类型详情
2022/03/20 Python