如何根据查询集中的值分配对象排名
How to assign ranking on objects based on a value in a queryset
我有一个查询集 returns 一个菜单列表,我想根据累积的票数为每个菜单分配一个等级有没有办法使用 django 查询表达式来实现这个?我也愿意接受任何其他建议。
查询集如下:
qs = Menu.objects.filter(Q(created_at__date__iexact=todays_date)).order_by('-投票')
而菜单class模型如下所示:
class Menu(models.Model):
"""Represents menu class model"""
restaurant = models.ForeignKey(Restaurant,null=True,blank=True,on_delete=models.CASCADE)
file = models.FileField(upload_to='menus/')
created_at = models.DateTimeField(auto_now_add=True)
updated_at = models.DateTimeField(auto_now=True)
uploaded_by = models.CharField(max_length=50, null=True, blank=True)
votes = models.IntegerField(default=0)
序列化查询集后 returns 以下数据:
[
{
"id": 10,
"file": "https://res.cloudinary.com/dw9bllelz/raw/upload/v1/media/menus/index_ah660c.jpeg",
"restaurant": "Burger King",
"votes": 10,
"created_at": "2021-06-03T09:33:05.505482+03:00"
},
{
"id": 9,
"file": "https://res.cloudinary.com/dw9bllelz/raw/upload/v1/media/menus/index_ah660c.jpeg",
"restaurant": "Texas Plates",
"votes": 2,
"created_at": "2021-06-03T09:33:05.505482+03:00"
},
{
"id": 8,
"file": "https://res.cloudinary.com/dw9bllelz/raw/upload/v1/media/menus/index_ah660c.jpeg",
"restaurant": "Carlito Dishes",
"votes": 2,
"created_at": "2021-06-03T09:33:05.505482+03:00"
},
{
"id": 7,
"file": "https://res.cloudinary.com/dw9bllelz/raw/upload/v1/media/menus/index_ah660c.jpeg",
"restaurant": "Kram Dishes",
"votes": 1,
"created_at": "2021-06-03T09:33:05.505482+03:00"
},
]
您可以使用数组中对象的 index 作为其索引,也可以使用 Window
functions [Django docs] and use the Rank
or DenseRank
(Reference [Django docs]) 函数根据需要计算排名:
from django.db.models import F, Window
from django.db.models.functions import Rank
qs = Menu.objects.filter(
Q(created_at__date__iexact=todays_date)
).annotate(
rank=Window(
expression=Rank(),
order_by=F('votes').desc(),
)
)
for menu in qs:
print(menu.rank, menu.votes)
我有一个查询集 returns 一个菜单列表,我想根据累积的票数为每个菜单分配一个等级有没有办法使用 django 查询表达式来实现这个?我也愿意接受任何其他建议。
查询集如下:
qs = Menu.objects.filter(Q(created_at__date__iexact=todays_date)).order_by('-投票')
而菜单class模型如下所示:
class Menu(models.Model):
"""Represents menu class model"""
restaurant = models.ForeignKey(Restaurant,null=True,blank=True,on_delete=models.CASCADE)
file = models.FileField(upload_to='menus/')
created_at = models.DateTimeField(auto_now_add=True)
updated_at = models.DateTimeField(auto_now=True)
uploaded_by = models.CharField(max_length=50, null=True, blank=True)
votes = models.IntegerField(default=0)
序列化查询集后 returns 以下数据:
[
{
"id": 10,
"file": "https://res.cloudinary.com/dw9bllelz/raw/upload/v1/media/menus/index_ah660c.jpeg",
"restaurant": "Burger King",
"votes": 10,
"created_at": "2021-06-03T09:33:05.505482+03:00"
},
{
"id": 9,
"file": "https://res.cloudinary.com/dw9bllelz/raw/upload/v1/media/menus/index_ah660c.jpeg",
"restaurant": "Texas Plates",
"votes": 2,
"created_at": "2021-06-03T09:33:05.505482+03:00"
},
{
"id": 8,
"file": "https://res.cloudinary.com/dw9bllelz/raw/upload/v1/media/menus/index_ah660c.jpeg",
"restaurant": "Carlito Dishes",
"votes": 2,
"created_at": "2021-06-03T09:33:05.505482+03:00"
},
{
"id": 7,
"file": "https://res.cloudinary.com/dw9bllelz/raw/upload/v1/media/menus/index_ah660c.jpeg",
"restaurant": "Kram Dishes",
"votes": 1,
"created_at": "2021-06-03T09:33:05.505482+03:00"
},
]
您可以使用数组中对象的 index 作为其索引,也可以使用 Window
functions [Django docs] and use the Rank
or DenseRank
(Reference [Django docs]) 函数根据需要计算排名:
from django.db.models import F, Window
from django.db.models.functions import Rank
qs = Menu.objects.filter(
Q(created_at__date__iexact=todays_date)
).annotate(
rank=Window(
expression=Rank(),
order_by=F('votes').desc(),
)
)
for menu in qs:
print(menu.rank, menu.votes)