简体   繁体   中英

Django order by vote percentage

I currently have a post that has upvotes and downvotes.

the model looks something like this

class Word(models.Model):
    name = models.CharField(max_length=250)
    upvotes = models.ManyToManyField(User, blank=True, related_name='threadUpVotes')
    downvotes = models.ManyToManyField(User, blank=True, related_name='threaddDownVotes')

in my views.py I have so far gotten this far

from django.db.models import F, Sum

words = Word.objects.filter(name__iexact='test').annotate(
            total_votes=Sum(F('upvotes') + F('downvotes'))).order_by('total_votes')

But I'm unsure what to do next to get it to rank by say the one with most upvotes vs downvotes.

You ham many to many field, You should use:

from django.db.models import F, Sum, Count

words = Word.objects.filter(name__iexact='test').annotate(
    total_votes=Count('upvotes') - Count('downvotes')).order_by('-total_votes')

or in your answer:

from django.db.models import F, Sum, Count
from django.db.models.functions.comparison import NullIf

words = Word.objects.filter(name__iexact='test').annotate(
    total_votes=Count('upvotes') / NullIf(
        Count('upvotes') + Count('downvotes')
    )).order_by('-total_votes')

I realized after I posted, I sumply had to divided the upvotes by the total number of votes and order in reverse.

words = Word.objects.filter(name__iexact='test').annotate(
            total_votes=Sum(F('upvotes'))/Sum(F('upvotes') + F('downvotes'))).order_by('-total_votes')

You can make use of aCount expression [Django-doc] with distinct=True [Django-doc] , otherwise you will count an upvote as many times there are downvotes and vice versa. We thus can determine the share of upvotes with:

from django.db.models import Count

words = Word.objects.filter(
    name__iexact='test'
).annotate(
    total_votes=Count('upvotes', distinct=True) / (Count('upvotes', distinct=True) + Count('downvotes', distinct=True))
).order_by('total_votes')

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM