Возникли проблемы с пониманием, почему я не могу фильтровать после среза в наборе запросов и что происходит.
stuff = stuff.objects.all()
stuff.count()
= 7
Если я тогда пойду
extra_stuff = stuff.filter(stuff_flag=id)
extra_stuff.count()
= 6. Все хорошо, и у меня есть новый набор запросов в дополнительных материалах.
stuff = stuff.objects.all()[:3]
extra_stuff = stuff.filter(stuff_flag=id)
Я получаю сообщение об ошибке «Невозможно отфильтровать запрос после того, как был взят фрагмент».
Как я могу дальше фильтровать набор запросов, где я ограничил количество результатов?
3 ответа
Вы не можете использовать filter()
после нарезки набора запросов. Ошибка довольно явная.
Cannot filter a query once a slice has been taken.
Вы можете сделать фильтр в Python
stuff = stuff.objects.all()[:3]
extra_stuff = [s for s in stuff if s.stuff_flag=='flag']
Чтобы получить количество элементов в дополнительном материале, просто используйте len()
extra_stuff_count = len(extra_stuff)
Выполнение фильтрации в Python будет работать нормально, когда размер stuff
очень мал, как в этом случае. Если бы у вас был намного больший фрагмент, вы могли бы использовать подзапрос, однако это также может иметь проблемы с производительностью, вам придется протестировать.
extra_stuff = Stuff.objects.filter(id__in=stuff, stuff_flag='flag')
Просто сделайте 2 запроса.
total_stuff = StuffClass.objects.count()
extra_stuff = StuffClass.filter(stuff_flag=id)[:3]
extra_stuff_count = len(StuffClass.filter(stuff_flag=id))
Обратите внимание, что если extra_stuff_count имеет значение несколько, например 3 или 300. Потому что для большего количества требуется больше памяти (в этом случае просто сделайте еще один запрос).
Django дает вам эту ошибку, потому что к этому моменту он уже получил элементы из базы данных. Метод filter
полезен только для уточнения запроса к базе данных перед его фактическим выполнением.
Поскольку вы получаете только три объекта, вы можете просто выполнить дополнительную фильтрацию в Django:
extra_stuff = [s for s in stuff if s.stuff_flag==id]
Но мне интересно, почему вы не делаете фильтр перед нарезкой.
Похожие вопросы
Новые вопросы
python
Python - это многопарадигмальный, динамически типизированный, многоцелевой язык программирования. Он разработан для быстрого изучения, понимания и использования, а также для обеспечения чистого и единообразного синтаксиса. Обратите внимание, что Python 2 официально не поддерживается с 01.01.2020. Тем не менее, для вопросов о Python, связанных с версией, добавьте тег [python-2.7] или [python-3.x]. При использовании варианта Python (например, Jython, PyPy) или библиотеки (например, Pandas и NumPy) включите его в теги.