Django values_list против значений

146

В Django, в чем разница между следующими двумя:

Article.objects.values_list('comment_id', flat=True).distinct()

против

Article.objects.values('comment_id').distinct()

Моя цель - получить список уникальных идентификаторов комментариев под каждым Article. Я прочитал документацию (и фактически использовал оба подхода). Результаты явно кажутся похожими.

Хасан Бэйг
источник
С values_list вы можете делать if self.id in Article.objects.values_list('comment_id', flat=True):, используя значения, которые вам нужны для доступа к словарю
dnaranjo
1
@dnaranjo - Вы могли бы, но почему бы просто не сделать Article.objects.filter(comment_id=self.id).exists()?
Sayse
1
Это ответ на другой вопрос
dnaranjo

Ответы:

250

values()Метод возвращает QuerySet , содержащие словари:

<QuerySet [{'comment_id': 1}, {'comment_id': 2}]>

values_list()Метод возвращает QuerySet , содержащие кортежи:

<QuerySet [(1,), (2,)]>

Если вы используете values_list()с одним полем, вы можете использовать flat=Trueдля возврата QuerySet с одним значением вместо 1-кортежа:

<QuerySet [1, 2]>
Алэсдэйр
источник
Ох, и нет никакой разницы между двумя визави, как distinct()используется, да?
Хасан Бэйг
2
Нет, я не думаю, что distinct()работает по-другому. Важно то, с какой структурой данных вы хотите работать.
Alasdair
3
В values()возвращает QuerySetи не является list. Хотя возвращаемый объект values()выглядит как a list, в некоторых случаях он не ведет себя как один. Например, он не будет json-сериализуемым, если мы не преобразуем его в «список»
Abhijit Ghate
@AbhijitGhate хорошая мысль, я обновил ответ, чтобы прояснить ситуацию.
Alasdair
2
Вы можете легко преобразовать возвращение values_listв истинный список Python, просто используя listфункцию:list(Article.objects.values_list('comment_id', flat=True).distinct())
inostia
55

ценности()

Возвращает QuerySet, который возвращает dictionaries, а не экземпляры модели, когда используется как итеративный.

values_list ()

Возвращает QuerySet, который возвращает list of tuples, а не экземпляры модели, когда используется как итеративный.

различны ()

отчетливо используются eliminate the duplicateэлементы.

Пример:

Article.objects.values_list('id', flat=True) # flat=True will remove the tuples and return the list   
[1, 2, 3, 4, 5, 6]

Article.objects.values('id')
[{'id':1}, {'id':2}, {'id':3}, {'id':4}, {'id':5}, {'id':6}]
Ибрагим Касим
источник
2
Так что это список словарей, которые возвращаются в случаеvalues
Хасан Бэйг
Просто чтобы уточнить: distinct()удаляет дубликаты элементов из результатов запроса, а не из базы данных.
oz19
5

Вы можете получить различные значения с:

set(Article.objects.values_list('comment_id', flat=True))
Питу
источник