當前位置: 首頁>>代碼示例 >>用法及示例精選 >>正文


Python Django QuerySet.distinct用法及代碼示例


本文介紹 django.db.models.query.QuerySet.distinct 的用法。

聲明

distinct(*fields)

返回在其 SQL 查詢中使用 SELECT DISTINCT 的新 QuerySet。這消除了查詢結果中的重複行。

默認情況下,QuerySet 不會消除重複行。實際上,這很少會成為問題,因為像 Blog.objects.all() 這樣的簡單查詢不會引入重複結果行的可能性。但是,如果您的查詢跨越多個表,則在評估 QuerySet 時可能會得到重複的結果。那時你會使用 distinct()

注意

order_by() 調用中使用的任何字段都包含在 SQL SELECT 列中。當與 distinct() 結合使用時,這有時會導致意外結果。如果您按相關模型中的字段排序,這些字段將添加到選定的列中,否則它們可能會使重複的行看起來不同。由於額外的列不會出現在返回的結果中(它們隻是為了支持排序),因此有時看起來返回的結果不明確。

同樣,如果您使用 values() 查詢來限製選定的列,則任何 order_by() (或默認模型排序)中使用的列仍將涉及並可能影響結果的唯一性。

這裏的寓意是,如果您使用distinct(),請注意按相關模型排序。同樣,當同時使用distinct() values() 時,按不在 values() 調用中的字段排序時要小心。

僅在 PostgreSQL 上,您可以傳遞位置參數 ( *fields ) 以指定應應用 DISTINCT 的字段名稱。這將轉換為 SELECT DISTINCT ON SQL 查詢。這就是區別。對於正常的distinct() 調用,數據庫在確定哪些行不同時比較每一行中的each 字段。對於具有指定字段名稱的distinct() 調用,數據庫將僅比較指定的字段名稱。

注意

指定字段名稱時,mustQuerySet 中提供 order_by(),並且 order_by() 中的字段必須以 distinct() 中的字段開頭,順序相同。

例如,SELECT DISTINCT ON (a) 為您提供 a 列中每個值的第一行。如果你不指定一個順序,你會得到一些任意的行。

示例(第一個之後的僅適用於 PostgreSQL):

>>> Author.objects.distinct()
[...]

>>> Entry.objects.order_by('pub_date').distinct('pub_date')
[...]

>>> Entry.objects.order_by('blog').distinct('blog')
[...]

>>> Entry.objects.order_by('author', 'pub_date').distinct('author', 'pub_date')
[...]

>>> Entry.objects.order_by('blog__name', 'mod_date').distinct('blog__name', 'mod_date')
[...]

>>> Entry.objects.order_by('author', 'pub_date').distinct('author')
[...]

注意

請記住, order_by() 使用已定義的任何默認相關模型排序。您可能必須按關係 _id 或引用字段顯式排序,以確保 DISTINCT ON 表達式與 ORDER BY 子句開頭的表達式匹配。例如,如果 Blog 模型通過 name 定義了 ordering

Entry.objects.order_by('blog').distinct('blog')

…不起作用,因為查詢將按 blog__name 排序,因此與 DISTINCT ON 表達式不匹配。您必須按關係 _id 字段(在本例中為 blog_id)或引用的字段(blog__pk)顯式排序,以確保兩個表達式匹配。

相關用法


注:本文由純淨天空篩選整理自djangoproject.com大神的英文原創作品 django.db.models.query.QuerySet.distinct。非經特殊聲明,原始代碼版權歸原作者所有,本譯文未經允許或授權,請勿轉載或複製。