Ответ
prefetch_related — это метод QuerySet в Django, предназначенный для оптимизации производительности путём сокращения количества SQL-запросов при доступе к связанным объектам. Он решает проблему N+1 запросов для отношений ManyToManyField и обратных ForeignKey.
В отличие от select_related, который использует JOIN на уровне SQL, prefetch_related выполняет отдельный запрос для связанных объектов и "соединяет" их на уровне Python.
Пример (проблема N+1):
# N+1 запросов: 1 для всех книг + N для авторов каждой книги
for book in Book.objects.all():
# Отдельный SQL-запрос на каждой итерации
print(book.authors.all())
Решение с prefetch_related:
# Всего 2 запроса: 1 для книг, 1 для всех связанных авторов
books = Book.objects.prefetch_related('authors')
for book in books:
# Данные об авторах уже загружены и доступны без доп. запросов
print(book.authors.all())
Когда использовать prefetch_related:
- Отношения "многие-ко-многим" (
ManyToManyField). - Обратные отношения "один-ко-многим" (обратный
ForeignKey). - Отношения
GenericForeignKey.
Используйте select_related для прямых отношений ForeignKey и OneToOneField, так как JOIN в этом случае эффективнее.