使用 F 对象从查询集中切换布尔字段

Posted

技术标签:

【中文标题】使用 F 对象从查询集中切换布尔字段【英文标题】:Toggle boolean fields from a Queryset using F objects 【发布时间】:2011-10-02 08:48:29 【问题描述】:

我已经用这些结果尝试了这些查询:

queryset.update(done=not F('boolean'))
'time': '0.001', 'sql': u'UPDATE "todo_item" SET "done" = True'

queryset.update(done=(F('boolean')==False))
'time': '0.001', 'sql': u'UPDATE "todo_item" SET "done" = False'

我想要的是这样的:

queryset.update(done=F('done'))       
'time': '0.002', 'sql': u'UPDATE "todo_item" SET "done" = "todo_item"."done"'

但是有

SET "done" = !"todo_item"."done"

切换布尔值

【问题讨论】:

【参考方案1】:

我正在开发 django-orm 扩展,并且已经部分实现了您的问题的解决方案。

>>> from django_orm.expressions import F
>>> from niwi.models import TestModel
>>> TestModel.objects.update(done=~F('done'))

# SQL:
UPDATE "niwi_testmodel" SET "done" = NOT "niwi_testmodel"."done"; args=()

https://github.com/niwibe/django-orm

是部分解决方案,不是很干净。到目前为止,仅适用于 postgresql。待会儿我会看看如何改进它。

更新:现在改进并适用于 postgresql、mysql 和 sqlite。

【讨论】:

【参考方案2】:
        #update_status
        update_status = (
          "UPDATE csv SET status = (NOT csv.status) "
          "WHERE id = %s")
        print(random_number)
        cursor.execute(update_status, (random_number))
        print("update_status")

【讨论】:

欢迎来到 ***!虽然此代码可能会回答问题,但提供有关 为什么 和/或 如何 此代码回答问题的附加上下文会提高其长期价值。【参考方案3】:

对于布尔值,您可以使用更 Pythonic 的not F(),对于字段的位否定,请使用~F()

【讨论】:

【参考方案4】:

这是标准方法,效果很好

conditional expressions

我会用一个更简单的例子来简单解释一下:)

假设我们有 Restaurant 对象(模型),其中有 is_closed 字段(BooleanField)

我们想要为具有 pk=1 的对象切换 is_closed,这个 sn-p 会这样做:

r1 = Restaurant.objects.get(pk=1).update(
    is_closed=Case(
        When(is_closed=True, then=False),
        default=True
    ))

【讨论】:

以上是关于使用 F 对象从查询集中切换布尔字段的主要内容,如果未能解决你的问题,请参考以下文章

JPQL 查询:选择一个布尔值,它是对象的两个字段的 AND

在 Django 中更新查询集中的一堆记录的最快方法

Django 在不使用字段查找的情况下从查询集中排除特定实例

django模板变量从查询集中构建表的字段数

Django Newbie - 使用多字段表单,如何消除查询集中的空字段

姜戈。如何在查询结果中添加字段?