Heim > Artikel > Backend-Entwicklung > Verwenden von Annotate für Group by in Django Orm
Verwendung
Die Methode „Gruppe nach“ des vorherigen ORM kann in Django 1.8 nicht mehr verwendet werden und Sie müssen annotate verwenden, um sie zu implementieren
Beispiel 1
Die ersten Werte werden verwendet. Wählen Sie die Felder aus, die gruppiert werden müssen (hier gruppieren Sie nach Benutzer-ID), und folgen Sie dann Annotate, um die erforderlichen Felder zu gruppieren und zu aggregieren (die Anzahl der Frage-IDs, die jeder Benutzer-ID entsprechen, und der Mindestwert von Katalog-ID sind erforderlich). ) und verwenden Sie dann Werte, um tatsächlich erforderliche Felder (Aliase der ursprünglichen Benutzer-ID und der aggregierten Felder) abzufragen.
Die ersten Werte werden verwendet, um die Felder anzugeben, die für die Gruppierung nach verwendet werden. Diese müssen Anzahl, Min. sein und andere Aggregatfunktionen (z. B. ist die Verwendung von F(" user_id")-Aliasing nicht möglich), ist keine Aggregation erforderlich, wenn Sie die endgültige Abfrage nicht benötigen
Der zweite Wert wird verwendet um das tatsächlich ausgewählte Feld anzugeben, und kann nur den Feldnamen nach der Annotation angeben (hier ist beispielsweise: user_id ist ein Feld, das zur Gruppierung verwendet wird und direkt übernommen werden kann, während andere Felder aggregiert werden müssen und die aggregierten Aliase qid und cid verwenden müssen . Wenn die Originaltabelle auch einen Feldstatus hat, wird dieses Feld nicht in Annotate aggregiert, sodass der Endwert das Feld nicht abfragen kann)
q = PxbNCEUserQuest.objects.filter(user_id=335).values("user_id").annotate(qid=Min("question_id"), cid=Min("catalog_id")).values("user_id", "qid", "cid") print q print q.query # 输出 [{'qid': 22, 'user_id': 335L, 'cid': 17}] SELECT `pxb_nce_user_quest`.`user_id`, MIN(`pxb_nce_user_quest`.`question_id`) AS `qid`, MIN(`pxb_nce_user_quest`.`catalog_id`) AS `cid` FROM `pxb_nce_user_quest` WHERE `pxb_nce_user_quest`.`user_id` = 335 GROUP BY `pxb_nce_user_quest`.`user_id` ORDER BY NULL
Beispiel 2
Wie Beispiel 1, aber hier wird die erste Anmerkung verwendet, um Felder zu gruppieren, und die zweite Anmerkung wird verwendet, um andere Felder einzeln mit einem Alias zu versehen
q = PxbNCEUserQuest.objects.filter(user_id=335).values("user_id").annotate(qid=Min("question_id"), cid=Min("catalog_id")).annotate(uid=F("user_id")).values("uid", "qid", "cid") print q print q.query # 输出: [{'qid': 22, 'uid': 335L, 'cid': 17}] SELECT MIN(`pxb_nce_user_quest`.`question_id`) AS `qid`, MIN(`pxb_nce_user_quest`.`catalog_id`) AS `cid`, `pxb_nce_user_quest`.`user_id` AS `uid` FROM `pxb_nce_user_quest` WHERE `pxb_nce_user_quest`.`user_id` = 335 GROUP BY `pxb_nce_user_quest`.`user_id` ORDER BY NULL
Beispiel:
SomeModel.objects.annotate(Count('somecol' ))
GROUP BY: alle Felder
SomeModel.objects.values ('name').annotate(Count('somecol'))
GROUP BY: Namensfeld , aggregiere somecol
SomeModel.objects.annotate(Count('somecol')).values ('name')
GROUP BY: Alle Felder, Abfragename
SomeModel .objects.values('name', 'pk').annotate(Count('somecol')). Values('pk')
GROUP BY: Name, PK-Feld, Abfrage-PK-Feld
SomeModel.objects.values('name').annotate(Count('somecol')). Values('pk')
GROUP BY: Name, PK-Feld, Abfrage-PK-Feld
Zugehöriges Wissen:
Die obige Abfragemethode ist zunächst möglicherweise schwer zu verstehen, aber wenn Sie die Gruppe nach Methode der ursprünglichen SQL-Anweisung vergleichen, werden Sie ein ähnliches Prinzip finden
In der In der alten Version von MySQL
wählen Sie a, b aus der t-Gruppe nach a aus, funktioniert normal, und das b-Feld übernimmt automatisch das erste, was einer impliziten Aggregation entspricht
Die obige Aussage kann in der neuen Version von MySQL nicht funktionieren, da der strikte Modus sql_mode=ONLY_FULL_GROUP_BY standardmäßig aktiviert ist. Die richtige Methode ist:
select a,max(b) as b from t group by, the Felder, die angezeigt werden müssen, um alle Abfragen zusammenzufassen
Wenn Sie die neue Version der MySQL-Syntax vergleichen, werden Sie feststellen, dass sie der Abfragemethode in ORM sehr ähnlich ist