Какова рекомендуемая идиома для проверки, дал ли запрос какие-либо результаты?
Пример:
orgs = Organisation.objects.filter(name__iexact = 'Fjuk inc')
# If any results
# Do this with the results without querying again.
# Else, do something else...
Я предполагаю, что есть несколько различных способов проверить это, но я хотел бы знать, как опытный пользователь Django сделает это. Большинство примеров в документации просто игнорируют случай, когда ничего не было найдено ...
django
django-queryset
Никлас
источник
источник
list
результата при наличии записей. Код там попадет в базу данных только один раз. Если бы они использовалиexist()
илиcount()
сначала проверили, будут ли возвращены записи, они дважды попадут в базу данных (один раз, чтобы проверить, один раз, чтобы получить записи). Это конкретная ситуация. Это не означает, что в общем случае предпочтительным способом узнать, будет ли запрос возвращать записи, является использование doif queryset:...
if not my_objects:
демонстрирующую, что именно так они и делают в документах. Все остальное совершенно не имеет значения, поэтому я не понимаю вашу точку зрения. С таким же успехом они могли бы сделать тысячу запросов, и это все равно было бы совершенно неактуально, так как это не является темой этого ответа, с чем я ясно заявляю, что согласен.get_object_or_404
работает, а не предпочтительный способ проверки наличия каких-либо элементов в наборе запросов . Выполнение list () для набора запросов приведет к извлечению всех объектов в наборе запросов, что было бы хуже, чем двойной запрос, если возвращено много строк..exists()
более эффективно, если qs не будет оцениваться.Начиная с версии 1.2, Django имеет QuerySet. Существует метод (), который является наиболее эффективным:
Но если вы все равно собираетесь оценивать QuerySet, лучше использовать:
Для получения дополнительной информации прочитайте документацию QuerySet.exists () .
источник
.get
не возвращает набор запросов. Возвращает объект. Так что погуглитеЕсли у вас огромное количество объектов, это может (иногда) быть намного быстрее:
В проекте, над которым я работаю, с огромной базой данных,
not orgs
400+ мс иorgs.count()
250 мс . В моих наиболее распространенных случаях использования (в тех случаях, когда есть результаты), эта техника часто сводится к тому, что до 20 мс. (Один случай, который я обнаружил, был 6.)Конечно, это может быть намного дольше, в зависимости от того, как далеко база данных должна искать, чтобы найти результат. Или даже быстрее, если он быстро его находит; YMMV.
EDIT: Это будет часто медленнее , чем
orgs.count()
если результат не найден, особенно если условие фильтрации вы на редкий один; в результате это особенно полезно в функциях представления, где вам нужно убедиться, что представление существует, или выдать Http404. (Где можно было бы надеяться, люди спрашивают URL-адреса, которые существуют чаще, чем нет.)источник
Чтобы проверить пустоту набора запросов:
или вы можете проверить первый элемент в наборе запросов, если он не существует, он вернет
None
:источник
if orgs.exists()
был покрыт ответом, который был предоставлен примерно за 5 лет до этого. Единственное, что этот ответ приносит к столу, который, возможно, является новым, являетсяif orgs.first()
. (Даже это спорно: он существенно отличается от делать тоorgs[0]
предложило около 5 лет назад тоже?) Вы должны развивать эту часть ответа: когда бы один хочет сделать это вместо других предложенных решений ранее?Самый эффективный способ (до django 1.2) это:
источник
Я не согласен с предикатом
Так должно быть
У меня была та же проблема с довольно большим набором результатов (~ 150 тыс. Результатов). Оператор не перегружен в QuerySet, поэтому результат фактически распаковывается в виде списка перед проверкой. В моем случае время исполнения сократилось на три порядка.
источник
Вы также можете использовать это:
if(not(orgs)): #if orgs is empty else: #if orgs is not empty
источник