【问题标题】:Modulo in django queryset?django查询集中的模数?
【发布时间】:2015-05-18 15:38:07
【问题描述】:

是否已经有办法根据 django queryset 中的id % 4 == 0 选择对象?

到目前为止,我发现的唯一解决方案是编写自定义转换,因为 Postgresql 似乎支持模数,但我遇到了错误。

这是我的代码:

from django.db.models import Lookup, Transform
from django.db.models.fields import Field, IntegerField, AutoField

class Modulo4(Transform):
    lookup_name = 'modulo4'

    def as_sql(self, compiler, connection):
        lhs, params = compiler.compile(self.lhs)
        return "%s %% 4" % lhs, params

AutoField.register_lookup(Modulo4)

foos = Foo.filter(id__modulo4=0)

并且在评估查询集时出现错误(使用foos.count() 或其他):

IndexError: tuple index out of range

引用一个 django 文件。这似乎是由于模数,因为我设法使自定义转换与doc example 一起工作。

关于如何实现这一目标的任何想法?

【问题讨论】:

    标签: django


    【解决方案1】:

    我手头没有 Django 1.8 来测试它,但看起来你可以使用 F with annotation 来执行此操作,如下所示:

    Foo.objects.annotate(idmod4=F('id') % 4).filter(idmod4=0)
    

    (Django 1.7 及更早版本不支持在annotate 中使用 F)


    对于 Django 1.7 及更早版本,您始终可以使用 .extra(),但它不是很漂亮:

    Foo.objects.extra(where=["id %% %s = 0"], params=[4])
    

    【讨论】:

    • 不幸的是,我正在使用 django 1.7 运行 :((应该在问题中指定它)
    • @stellasia 用 Django 1.7 唯一可用的方法更新了我的答案
    • 似乎不适用于 %d 参数,但我可以在没有选项的情况下做到这一点。非常感谢!
    • @stellasia 抱歉,应该只是%s
    猜你喜欢
    • 1970-01-01
    • 2012-12-15
    • 2011-11-13
    • 2010-09-26
    • 2018-12-20
    • 1970-01-01
    • 1970-01-01
    • 2018-12-04
    • 2013-06-30
    相关资源
    最近更新 更多