【问题标题】:Django queryset ordering by fieldsDjango 查询集按字段排序
【发布时间】:2020-08-16 09:03:27
【问题描述】:

我正在使用 django 2,在我的列表视图中,我想通过 likecount 和 datetime 字段对查询集进行排序。主要目标是在今天获得最多赞的帖子。就像,我想显示今天最喜欢的帖子。 就像今天的前 10 个帖子(最喜欢)。我尝试了很多方法,但无法弄清楚。我希望你们能帮助我。

我的models.py:

class post(models.Model):
    parent = models.ForeignKey("self", on_delete=models.CASCADE, blank=True, null=True)
    title = models.CharField(max_length=100)
    image = models.ImageField(upload_to='post_pics', null=True, blank=True)
    content = models.TextField()
    likes = models.ManyToManyField(User, related_name='likes', blank=True)
    date_posted = models.DateTimeField(default=timezone.now)
    author = models.ForeignKey(User, on_delete=models.CASCADE)
    restrict_comments = models.BooleanField(default=False)
    watchlist = models.ManyToManyField(User, related_name='watchlist', blank=True)

    def __str__(self):
        return self.content

    class Meta:
        ordering = ['-date_posted', 'title']

    def get_absolute_url(self):
        return reverse ('blog-home')

    def total_likes(self):
        return self.likes.count()

我的意见.py:

@login_required
def most_likes(request):
    posts = post.objects.annotate(like_count=Count('likes')).order_by('-like_count', '-date_posted')
    context = {'posts': posts}

    return render(request, 'blog/most_likes.html', context)

【问题讨论】:

  • 一切看起来都很好。你目前得到的输出是什么?
  • 它按日期给出最喜欢的帖子。就像我的帖子是 5 个月大并且是最近的,它会获得顶部喜欢它返回顶部的帖子。就像,如果没有人超过当前帖子的点赞数,最喜欢的帖子将永远保持在顶部。我想订购 24 小时。它将在 24 小时内返回热门帖子。 @revliscano

标签: python django django-models django-views django-queryset


【解决方案1】:

如果我没听错,您已经按照您想要的字段(like_count 和 date_posted)对查询集进行了排序,但是您仍然缺少仅获取所需时间段的结果的部分.

如果是这种情况,那么您缺少的是过滤查询集。你需要这样的东西(获取最近 10 天的帖子,按日期和点赞数排序):

import datetime as dt


@login_required
def most_likes(request):
    delta = dt.timedelta(days=10)
    posts = post.objects.filter(date_posted__gt=(dt.datetime.now() - delta)) \
        .annotate(like_count=Count('likes')).order_by('-like_count', '-date_posted')
    context = {'posts': posts}

    return render(request, 'blog/most_likes.html', context)

现在,我将尝试将想要过滤数据的所需时间段的值作为查询参数传递,因此我可以执行以下操作:

delta = dt.timedelta(days=request.GET.get('days'))

【讨论】:

  • 最后查询参数部分没看懂。在最后一部分你没有提到天数。 @revliscano
  • 是的,我的意思是,我只是建议您考虑将天数作为查询参数传递给该视图@Cavinblake
  • 谢谢,一切正常。但日期时间警告引发2020-05-02 19:43:59,467: /home/neso/.virtualenvs/django2/lib/python3.6/site-packages/django/db/models/fields/__init__.py:1421: RuntimeWarning: DateTimeField post.date_posted received a naive datetime (2020-04-22 19:43:59.466748) while time zone support is active. 2020-05-02 19:43:59,467: RuntimeWarning) 这是我得到的警告。否则一切正常
  • 是的,这是因为 datetime.now() 没有时区信息,但您的 date_posted 字段需要它。在大多数用例中这应该不是问题,但是如果您想了解有关如何传递该时区信息的更多信息,您可以查看此问题的答案:stackoverflow.com/questions/2331592/…
  • 如果我没有在查询参数中传递天数。我的意思是,如果我不添加查询参数的最后一行,而是只使用 ** delta = dt.timedelta(days=10) ** 这一行。会不会造成什么问题? @revliscano
猜你喜欢
  • 2010-12-11
  • 2015-08-31
  • 2012-12-20
  • 1970-01-01
  • 2012-07-30
  • 1970-01-01
  • 2019-08-14
  • 2011-05-08
  • 2022-11-22
相关资源
最近更新 更多