什么是无限极分类呢?

无限极分类简单点说就是一个类可以分成多个子类,然后一个子类又可以分另外多个子类这样无限分下去,
就好象windows可以新建一个文件夹,然后在这个文件夹里又可以建一些个文件夹,在文件夹底下还可以建一些文件夹一样.

无限极分类

1
2
3
4
5
6
7
8
9
10
衣服
上衣
短袖
卫衣
裤子
牛仔裤
休闲裤
鞋子
运动鞋
休闲鞋

无限极分类应用场景很广泛,例:
帖子的回复功能
课程的目录章节

基于python,结合django+vue实现无限极分类(递归层级结构)

在myapp中model.py文件下
1
2
3
4
5
6
7
8
9
class Cate(models.Model):
#id是主键,自增
#分类名称
name = models.CharField(max_length=200,null=True)
#父级分类id
pid = models.IntegerField()

class Meta:
db_table = 'cate'
数据库配置数据

无限极分类数据库配置

使用drf框架进行序列化
1
2
3
4
5
6
7
8
9
#导包
from rest_framework import serializers
from .models import Cate

#序列化类
class CateSer(serializers.ModelSerializer):
class Meta:
model = Cate
fields = '__all__'
写一个用来进行递归的方法,进行层级结构划分
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
def Xtree(datas):
lists = []
tree = {}
for item in datas:
tree[item['id']] = item
print(tree[item['id']])
for i in datas:
if not i['pid']:
root = tree[i['id']]
lists.append(root)
else:
parent_id = i['pid']
if 'child' not in tree[parent_id]:
tree[parent_id]['child'] = []
tree[parent_id]['child'].append(tree[i['id']])
return lists
写视图接口并分配路由
1
2
3
4
5
6
7
8
9
10
11
12
from .myser import CateSer
from .cengji import Xtree

# 递归层级分类
class MyTree(APIView):
def get(self,request):
cates = Cate.objects.all()
ser = CateSer(cates,many=True)
trees = Xtree(ser.data)
return Response(trees)
#分配url
# path('tree/',MyTree.as_view()),
测试接口

后端接口返回数据

前端使用递归组件渲染

所谓递归组件: 就是组件可以在它们自己的模板中调用自身,
不过它们只能通过 name 选项来做这件事,例如给组件设置属性 name: ‘Reply’,
然后在模板中就可以使用 Reply 调用自己进行递归调用了

设置Reply.vue
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
<template>
<div>
<li>
<div :class="[data.id==0 ? 'root':'','reply']">
{{data.name}}
</div>
<ul v-if="data.child && data.child.length>0">
<Reply v-for="c in data.child" :key="c.id" :data="c"></Reply>
</ul>
</li>
</div>
</template>


<script>
export default {
name:"Reply",//递归需要设置name属性,才能在模板中调用自身
data(){
return{

}
},
props:['data'],
mounted() {

},
}
</script>


<style>
.reply{
padding-left: 4px;
border-left: 1px solid #eee;
}
ul{
padding-left: 20px;
list-style: none;
}
.root{
display: none;
}
</style>
在其他组件调用Reply.vue
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
<!-- 
import cengji from '@/components/cengji'
{
path:'/cengji',
name:'cengji',
component:cengji
},
-->
<template>
<div>
<Reply :data="data"></Reply>
</div>
</template>


<script>
// import {config,formatXml} from '../config'
// import mh_test from './mh_test.vue'
import Reply from './Reply'
// import md5 from 'js-md5'

export default {
data(){
return{
data:{},
online:0,
}
},
components:{
Reply
},
mounted() {
this.get_token()
},
methods: {
get_token(){
this.axios({
url:"http://localhost:8000/tree/",
method:"GET"
}).then(resp=>{
console.log(resp)
var tree = {'id':0,name:"123"}
tree['child'] = resp.data
this.data = tree
console.log(this.data)
})
}
},
}
</script>

<style>
.on {
background: #cdcbff;
}
.off {
background: #fefdff;

}
</style>
前端结果展示

无限极分类前端结果展示

评论





载入天数...载入时分秒...

Blog content follows the Attribution-NonCommercial-ShareAlike 4.0 International (CC BY-NC-SA 4.0) License

Use WZH as theme, total visits times