orm性能相关
小结
-
尽量不查对象,能用values()
-
select_related('classes') 连表查询 多对一 一对一
-
prefetch_related('classes') 子查询 多对一 多对多
-
only('name') 指定某些字段 defer 指定排除某些字段
-
queryset 特性
ORM操作 *****
- only
- defer
- seleted_related
- prefetch_related
提高查询效率的方法 — selected_related与prefetch_related
class Depart(models.Model): 5个部门 title = models.CharField(...) class User(models.Model): 10个用户 name = models.CharField(...) email = models.CharField(...) dp = models.FK(Depart)
比较low的方法 —— 11次单表查询
result = User.objects.all() for item in result: print(item.name,item.dp.title)
selected_related方法
—— 只支持~OneToOne与ForeignKey
—— 主动做连表查询(1次连表查询相当于2次单表查询)
result = User.objects.all().seleted_related('dp') for item in result: print(item.name,item.dp.title)
—— 问题:如果链表多,性能越来越差。—— 但是一般情况下表不会连的特别多!
prefetch_related方法
—— 除了外键与一对一关系还支持多对多!
—— 子查询<多次单表查询>(2次单表查询 )
# select * from user ; # 通过python代码获取:dp_id = [1,2] # select * from depart where id in dp_id —— 只找相关的dep result = User.objects.all().prefetch_related('dp') for item in result: print(item.name,item.dp.title)
—— 注意:1次单表查询要比1次连表查询效率高。
数据量比较大,不会使用FK,数据放在一张表中,允许出现数据冗余 *****
—— 为什么要用ForeignKey?
1、不使用FK的话,浪费硬盘!使用FK可以节省硬盘空间
2、但是同时降低了查询速度,因为连表操作的效率要低于单表的操作
3、进行字段约束
4、但是业务的数据量大的话,不会使用FK,为了让用户体验好,查询速度快,放在一张表中——单表查询快。