377 Stimmen

Wie filtere ich Abfrageobjekte nach Datumsbereich in Django?

Ich habe ein Feld in einem Modell wie:

class Sample(models.Model):
    date = fields.DateField(auto_now=False)

Nun muss ich die Objekte nach einem Datumsbereich filtern.

Wie kann ich alle Objekte filtern, die ein Datum zwischen 1-Jan-2011 y 31-Jan-2011 ?

595voto

crodjer Punkte 12644

U

Sample.objects.filter(date__range=["2011-01-01", "2011-01-31"])

Oder wenn Sie nur versuchen, nach Monaten zu filtern:

Sample.objects.filter(date__year='2011', 
                      date__month='01')

bearbeiten

Wie Bernhard Vallant schon sagte, wenn Sie ein Queryset wollen, das die specified range ends sollten Sie berücksichtigen seine Lösung die gt/lt (größer/weniger als) verwendet.

309voto

Bernhard Vallant Punkte 46005

Sie können verwenden djangos filter con datetime.date Objekte :

import datetime
samples = Sample.objects.filter(sampledate__gte=datetime.date(2011, 1, 1),
                                sampledate__lte=datetime.date(2011, 1, 31))

137voto

cademan Punkte 1191

Wenn Sie django Bereiche mit einem Filter tun, stellen Sie sicher, dass Sie den Unterschied zwischen der Verwendung eines Datum-Objekts und eines datetime-Objekts kennen. Wenn Sie jedoch ein Datetime-Objekt für das Enddatum verwenden, werden die Einträge für diesen Tag nicht berücksichtigt, wenn die Uhrzeit nicht festgelegt ist.

from datetime import date, timedelta

startdate = date.today()
enddate = startdate + timedelta(days=6)
Sample.objects.filter(date__range=[startdate, enddate])

gibt alle Einträge von startdate bis enddate zurück, einschließlich der Einträge an diesen Tagen. Ein schlechtes Beispiel, da hier die Einträge eine Woche in die Zukunft zurückgegeben werden, aber Sie verstehen, was ich meine.

from datetime import datetime, timedelta

startdate = datetime.today()
enddate = startdate + timedelta(days=6)
Sample.objects.filter(date__range=[startdate, enddate])

fehlen 24 Stunden an Einträgen, je nachdem, wie die Zeit für die Datumsfelder eingestellt ist.

31voto

trojjer Punkte 609

Sie können die "Impedanzfehlanpassung" umgehen, die durch die mangelnde Präzision der DateTimeField/date Objektvergleich - der bei der Verwendung von Bereich -- durch Verwendung eines datetime.timedelta um einen Tag zum letzten Datum im Bereich hinzuzufügen. Dies funktioniert wie folgt:

start = date(2012, 12, 11)
end = date(2012, 12, 18)
new_end = end + datetime.timedelta(days=1)

ExampleModel.objects.filter(some_datetime_field__range=[start, new_end])

Wie bereits erwähnt, werden Datensätze am letzten Tag ignoriert, wenn dies nicht der Fall ist.

Bearbeitet, um die Verwendung von datetime.combine -- scheint es logischer zu sein, beim Vergleich mit einer Datumsinstanz zu bleiben DateTimeField statt sich mit (verwirrenden) Wegwerfprodukten herumzuschlagen datetime Objekte. Weitere Erläuterungen finden Sie in den Kommentaren unten.

12voto

Ahmed Elgammudi Punkte 524

Sie können "__range" verwenden zum Beispiel :

from datetime import datetime
start_date=datetime(2009, 12, 30)
end_date=datetime(2020,12,30)
Sample.objects.filter(date__range=[start_date,end_date])

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X