django - 如何提高查询性能n+1
问题描述
我有以下内容:
#models:py
class Author(models.Model):
name = models.CharField(max_length=20)
class Book(models.Model):
author = ForeignKey(Author)
title = models.CharField(max_length=20)
class Comment(models.Model):
book = ForeignKey(book)
title = models.CharField(max_length=20)
#views.py
class AuthorBookComment(ListView):
model = Author
paginate_by = 5
template = “template.html”
#template.html
{% for author in object_list %}
<h2>{{ author.name }}</h2>
{% for book in author.book_set.all %}
<h3>{{book.title}}</h3>
{% for comment in book.comment_set.all %}
{{comment.title}}<br/>
{% endfor %}
{% endfor %}
{% endfor %}
<<pagination code>>
这个想法是显示所有作者及其书籍和评论(如果存在)。
挑战: 1. 随着数据量的增加,性能下降(sql 请求数 = n+1)。2. 作者集与作者+书籍+评论集的分页。
问题:如何改进/优化上述内容?
我尝试了各种版本的 select_related() 和 prefetch_related()。结果如下,但仍然不够高效 + 大数据集被返回。有没有更好的办法?
查询、TimeMs:查询集 230、106
:Author.objects.all()
229、105:Author.objects.all().prefetch_related(book_set').all()
179、88:Author.objects.all().prefetch_related ('book_set__comment_set').all()
解决方案
在这些情况下,您应该始终使用select_related()或prefetch_related() 预先加载数据。
推荐阅读
- python - 无法使用网页中的scrapy提取javascript
- vb.net - 在 Visual Basic .net 中使用 HID 条形码扫描仪
- android - Android:从UI线程启动一个工作线程挂起应用程序
- python - sleep_until 的 Python 版本
- javascript - 通过 php 和数组数据创建动态链接和 onClick
- c++ - 类中成员的类型似乎会影响类中其他成员的初始化
- c# - 如何从作为类属性的列表中返回元素
- encoding - 参数中编码特殊字符导致spring boot合约测试查询不匹配问题
- html - 尽管z-Index,鼠标悬停图像显示推送文本
- amazon-s3 - 在 AWS S3、cloudfront 和 route53 上使用掩码重定向