2013-08-07 8 views
7

Ist es möglich, die folgende mysql-Abfrage in Django zu reproduzieren, ohne die select-Methode zu verwenden?Django-Gruppe nach Datum und SUM-Werten

MariaDB [db1]> SELECT datetime, SUM(datas) FROM table AND datetime BETWEEN '2013-07-26 13:00:00' AND '2013-07-26 23:00:00' GROUP BY datetime; 

Um diese Art von Ergebnis:

+---------------------+-----------+ 
| datetime   | SUM(data) | 
+---------------------+-----------+ 
| 2013-07-26 13:00:00 |  489 | 
| 2013-07-26 14:00:00 |  2923 | 
| 2013-07-26 15:00:00 |  984 | 
| 2013-07-26 16:00:00 |  2795 | 
| 2013-07-26 17:00:00 |  1308 | 
| 2013-07-26 18:00:00 |  1365 | 
| 2013-07-26 19:00:00 |  1331 | 
| 2013-07-26 20:00:00 |  914 | 
| 2013-07-26 21:00:00 |  919 | 
| 2013-07-26 22:00:00 |  722 | 
| 2013-07-26 23:00:00 |  731 | 
+---------------------+-----------+ 
11 rows in set (1.45 sec) 

Edit: Ich diese Art der Abfrage für jetzt bekam:

>>> value = table.objects.filter(datetime__range=('2013-07-26 13:00:00', 
'2013-07-26 23:00:00')).values('datetime', 'data').annotate(Sum('data')) 

>>> print value.query 
SELECT `table`.`datetime`, `table`.`data` SUM(`table`.`imps`) AS `data__sum` 
FROM `table` 
WHERE `table`.`datetime` BETWEEN 2013-07-26 13:00:00 
and 2013-07-26 23:00:00 GROUP BY `table`.`datetime`, 
`table`.`data` ORDER BY NULL 

Warum Summe sowohl Datetime und Daten arbeiten?

Ich versuchte überall auf Django Doc, hier auf Stapel, aber fand nicht etwas mit meinem Problem kohärent. Irgendwelche Vorschläge?

+1

Welche SQL hat Ihr queryset generieren? Sie können 'print values.query' verwenden. –

+0

Die Reihenfolge von' .annotate() 'und' .values ​​() ' –

Antwort

6

Hmm Sie Count verwenden, sollten Sie Sum, verwenden und values() wird bestimmen, was in GROUP BY geht so sollten Sie values('datetime') nur verwenden. Ihre queryset sollte wie folgt sein:

from django.db.models import Sum 

values = self.model.objects.filter(
    datetime__range=(self.dates[0], self.dates[1]) 
).values('datetime').annotate(data_sum=Sum('data')) 

obwohl ich bin mir nicht so sicher über die Reihenfolge der filter(), so könnte es sein:

values = self.model.objects.values('datetime').annotate(data_sum=Sum('data')).filter(
    datetime__range=(self.dates[0], self.dates[1]) 
) 

ich Sie beide versuchen würden, will erraten dann . Wenn Sie die rohe Abfrage von diesen queryset sehen möchten, verwenden Queryset.query:

print self.model.objects.filter(
    datetime__range=(self.dates[0], self.dates[1]) 
).values('datetime').annotate(data_sum=Sum('data')).query.__str__() 

So können Sie sicherstellen, dass Sie die richtige Abfrage erhalten.

Ich hoffe, es hilft.

+1

thx ändern, warum nach dem Kommentar filtern? – tbenett

+1

Es ist nur ich bin mir nicht sicher über die Ergebnisabfrage von ihnen, so könnte es entweder sein, verwenden Sie 'query .__ str __()', um die Abfrage zu überprüfen, die Sie benötigen. Überprüfen Sie auch meine Antwort sorgfältig, sollten Sie 'Werte ('Datetime')' nur –

+0

können Sie die Antwort bearbeiten, um anzugeben, welche Antwort richtig war? – Jglstewart

4

order_by() erhalten Sie GROUP BY:

values = self.model.objects.filter(datetime__range=(
    self.dates[0], self.dates[1])) \ 
    .values('datetime') \ 
    .annotate(data_sum=Sum('datas') \ 
    .order_by()) 
+0

Funktioniert nicht, sorry: SELECT 'table'.datetime',' table''data' FROM 'table' WHERE' table''datetime' ZWISCHEN 2013-07-26 13:00:00 und 2013-07 -26 23:00:00) ORDER BY 'table''datetime' ASC – tbenett

+0

Wie wäre es jetzt? –

+0

Es ist in Ordnung, ich benutze Hieu Nguyen Methode und das Problem kam von den Werten ('Datetime', 'Daten') – tbenett