是不是“更好”了? 有更新字段或 COUNT 查询吗?

发布于 2024-07-11 18:35:11 字数 1246 浏览 8 评论 0原文

在我正在开发的 Django 应用程序中,我遇到了这样的情况:

class Parent(models.Model):
    name = models.CharField(...)

    def num_children(self):
        return Children.objects.filter(parent=self).count()

    def avg_child_rating(self):
        return Child.objects.filter(parent=self).aggregate(Avg('rating'))

class Child(models.Model):
    name = models.CharField(...)
    parent = models.ForeignKey(Parent)
    rating = models.IntegerField(default=0)

我计划经常访问 avg_child_ rating 。 如果我执行以下操作,是否会进行优化:

class Parent(models.Model):
    ...
    num_children = models.IntegerField(default=0)
    avg_child_rating = models.FloatField(default=0.0)

def update_parent_child_stats(sender, instance, **kwargs):
    num_children = Child.objects.filter(parent=instance.parent)
    if instance.parent.num_children != num_children:
        instance.parent.num_children = num_children
        instance.parent.avg_child_rating = Child.objects.filter(instance.parent=self).aggregate(Avg('rating'))

post_save.connect(update_parent_child_stats, sender=Child)
post_delete.connect(update_parent_child_stats, sender=Child)

现在的区别是,每次创建/评级/删除子项时,父对象都会更新。 我知道创建/评级会经常进行。

什么更

In a Django App I'm working on I've got this going on:

class Parent(models.Model):
    name = models.CharField(...)

    def num_children(self):
        return Children.objects.filter(parent=self).count()

    def avg_child_rating(self):
        return Child.objects.filter(parent=self).aggregate(Avg('rating'))

class Child(models.Model):
    name = models.CharField(...)
    parent = models.ForeignKey(Parent)
    rating = models.IntegerField(default=0)

I plan on accessing avg_child_rating often. Would it be optimizing if I did the following:

class Parent(models.Model):
    ...
    num_children = models.IntegerField(default=0)
    avg_child_rating = models.FloatField(default=0.0)

def update_parent_child_stats(sender, instance, **kwargs):
    num_children = Child.objects.filter(parent=instance.parent)
    if instance.parent.num_children != num_children:
        instance.parent.num_children = num_children
        instance.parent.avg_child_rating = Child.objects.filter(instance.parent=self).aggregate(Avg('rating'))

post_save.connect(update_parent_child_stats, sender=Child)
post_delete.connect(update_parent_child_stats, sender=Child)

The difference now is that every time a child is created/rated/deleted, the Parent object is updated. I know that the created/rating will be done often.

What's more expensive?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

毁我热情 2024-07-18 18:35:11

取决于问题的严重程度。
如果您预计会有大量写入流量,这可能是一个问题。 扩展写入比扩展读取(复制、缓存等)要困难得多。也就是说,您可能可以走很长一段路,而不会因为这个额外的查询而导致任何问题。

根据您的统计数据的最新程度,您可以让其他进程(非网络会话)完成并每晚更新这些统计数据。

Depends on the scale of the problem.
If you anticipate a lot of write traffic, this might be an issue. It's much harder to scale writes than reads (replicate, caching etc.) That said, you can probably going a long way without this extra query causing you any problems.

Depending on how up-to-date your stats must be you could have some other process (non-web session) come through and update these stats nightly.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文