Verkrijg duidelijke waarden van Queryset per veld

Ik heb dit model:

class Visit(models.Model):
    timestamp  = models.DateTimeField(editable=False)
    ip_address = models.IPAddressField(editable=False)

Als een gebruiker meerdere keren op één dag een bezoek brengt, hoe kan ik dan filteren op unieke rijen op basis van het ip-veld?(ik wil de unieke bezoeken voor vandaag)

today = datetime.datetime.today()
yesterday = datetime.datetime.today() - datetime.timedelta(days=1)
visits = Visit.objects.filter(timestamp__range=(yesterday, today)) #.something?

BEWERKEN:

Ik zie dat ik kan gebruiken:

Visit.objects.filter(timestamp__range=(yesterday, today)).values('ip_address')

om een ​​ValuesQuerySet te krijgen van alleen de ip-velden. Nu ziet mijn QuerySet er als volgt uit:

[{'ip_address': u'127.0.0.1'}, {'ip_address': u'127.0.0.1'}, {'ip_address':
 u'127.0.0.1'}, {'ip_address': u'127.0.0.1'}, {'ip_address': u'127.0.0.1'}]

Hoe filter ik dit op uniciteit zonder de QuerySet te evalueren en de db-hit te nemen?

# Hope it's something like this...
values.distinct().count()

Antwoord 1, autoriteit 100%

Wat je wilt is:

Visit.objects.filter(stuff).values("ip_address").annotate(n=models.Count("pk"))

Wat dit doet is alle ip_adressen ophalen en vervolgens het aantal primaire sleutels (ook wel het aantal rijen genoemd) voor elk ip-adres.


Antwoord 2, autoriteit 67%

Met Alex Answer heb ik ook de n:1 voor elk item. Zelfs met een aparte() clausule.

Het is raar omdat dit het goede aantal items retourneert:

Visit.objects.filter(stuff).values("ip_address").distinct().count()

Maar toen ik “Visit.objects.filter(stuff).values(“ip_address”).distinct()” herhaal, kreeg ik veel meer items en enkele duplicaten…

BEWERKEN:

De filterclausule veroorzaakte problemen bij mij. Ik was aan het filteren met een ander tabelveld en er werd een SQL JOIN gemaakt die de verschillende dingen brak.
Ik heb deze hint gebruikt om de zoekopdracht te zien die echt werd gebruikt:

q=Visit.objects.filter(myothertable__field=x).values("ip_address").distinct().count()
print q.query

Vervolgens heb ik de klas teruggezet waarop ik de query deed en het filter om een ​​join te hebben die niet afhankelijk is van een “Bezoek”-ID.

hoop dat dit helpt


Antwoord 3, autoriteit 8%

De vraag is anders dan de titel suggereert. Als je set-achtig gedrag van de database wilt, heb je zoiets als dit nodig.

x = Visit.objects.all().values_list('ip_address', flat=True).distinct()

Het zou je zoiets moeten geven voor x.

[1.2.3.4, 2.3.4.5, ...]

Waar

len(x) == len(set(x))

Retourneert True

Other episodes