Myślę, że głównym problemem jest to, że mieszasz operacje, które użyte w adnotacji generują zgrupowany zestaw zapytań, taki jak sum, z operacją, która po prostu tworzy nowe pole dla każdego rekordu w danym zestawie zapytań, np. yesterday_count=Window(expression=Lag("count"))
.
Tak więc zamawianie naprawdę ma tutaj znaczenie. Więc kiedy spróbujesz:
WidgetCount.objects.distinct("date").annotate(date=Trunc("time", "day"), yesterday_count=Window(expression=Lag("count")))
Wynikowy zestaw zapytań to po prostu adnotacja WidgetCount.objects.distinct("data"), bez grupowania.
Sugerowałbym oddzielenie operacji, aby łatwiej było zrozumieć, co się dzieje, i zauważ, że iterujesz po obiekcie Pythona, więc nie musisz wykonywać żadnych nowych zapytań!
Uwaga dotycząca użycia operacji SUMA jako przykładu, ponieważ otrzymuję nieoczekiwany błąd z operatorem FirstValue. Więc piszę z Sumem, aby zademonstrować ideę, która pozostaje ta sama. Pomysł powinien być taki sam dla pierwszej wartości, zmieniając tylko acc_count=Sum("count")
to first_count=FirstValue("count")
for truncDate_groups in Row.objects.annotate(trunc_date=Trunc('time','day')).values("trunc_date")\
.annotate(acc_count=Sum("count")).values("acc_count","trunc_date")\
.order_by('trunc_date')\
.annotate(y_count=Window(Lag("acc_count")))\
.values("trunc_date","acc_count","y_count"):
print(truncDate_groups)
WYJŚCIE:
{'trunc_date': datetime.datetime(2020, 1, 20, 0, 0, tzinfo=<UTC>), 'acc_count': 65, 'y_count': None}
{'trunc_date': datetime.datetime(2020, 1, 21, 0, 0, tzinfo=<UTC>), 'acc_count': 75, 'y_count': 162}
{'trunc_date': datetime.datetime(2020, 1, 22, 0, 0, tzinfo=<UTC>), 'acc_count': 162, 'y_count': 65}
Okazuje się, że operator FirstValue wymaga użycia funkcji Windows, więc nie możesz zagnieździć FirtValue, a następnie obliczyć opóźnienia, więc w tym scenariuszu nie jestem do końca pewien, czy możesz to zrobić. Pytanie brzmi, jak uzyskać dostęp do kolumny First_Value bez zagnieżdżania okien.