2009-05-08 19 views
26

So che Django 1.1 ha alcuni nuovi metodi di aggregazione. Tuttavia, non riuscivo a capire equivalente del seguente query:Django equivalente di COUNT con GROUP BY

SELECT player_type, COUNT(*) FROM players GROUP BY player_type; 

E 'possibile con API query modelli di Django 1.1 del o devo solo usare SQL pianura?

+0

Possibile duplicato di [Django: come fare SELECT COUNT (\ *) GROUP BY e ORDER BY] (http://stackoverflow.com/questions/19101665/django-how-to-do-select-count -group-by-and-order-by) –

risposta

55

Se si utilizza Django 1.1 beta (tronco):

Player.objects.values('player_type').order_by().annotate(Count('player_type')) 
  • values('player_type') - per includere solo il campo player_type nella clausola GROUP BY.
  • order_by() - per l'esclusione possibile l'ordine predefinito che può causare l'inclusione dei campi non necessari in SELECT e GROUP BY.
+13

+1 per .order_by() –

14

Django 1.1 supporta i metodi di aggregazione come il conteggio. È possibile trovare the full documentation here.

Per rispondere alla tua domanda, è possibile utilizzare qualcosa sulla falsariga di:

from django.db.models import Count 
q = Player.objects.annotate(Count('games')) 
print q[0] 
print q[0].games__count 

questo dovrà lieve ritocco a seconda del modello attuale.

Modifica: il frammento sopra riportato genera aggregazioni per ogni oggetto. Se si desidera aggregazione in un particolare campo nel modello, è possibile utilizzare il metodo values:

from django.db.models import Count 
q = Player.objects.values('playertype').annotate(Count('games')).order_by() 
print q[0] 
print q[0].games__count 

order_by() è necessario perché i campi che sono l'ordinamento di default vengono selezionati automaticamente anche se non sono esplicitamente passati al values(). Questa chiamata a order_by() cancella qualsiasi ordine e fa sì che la query si comporti come previsto.

Inoltre, se si desidera contare il campo che viene utilizzato per il raggruppamento (equivalente a COUNT(*)), è possibile utilizzare:

from django.db.models import Count 
q = Player.objects.values('playertype').annotate(Count('playertype')).order_by() 
print q[0] 
print q[0].playertype__count 
+0

Questa chiamata genererà una clausola 'GROUP BY' errata - con tutti i campi del modello inclusi. Ma l'autore ha chiesto solo un raggruppamento di campi. –

+0

Stavo cercando di dare un esempio generale e puntare alla documentazione. Questo è il motivo per cui ho detto che il mio snippet doveva essere modificato. Ho aggiunto altri esempi alla mia risposta ora. Grazie per il commento. :) –