Django ORM:exclude不返回预期结果

时间:2017-09-05 06:33:53

标签: django django-queryset django-orm

Django 1.11.4

我只想选择丢失物品的相框。 如果项目丢失,lost_day不为空。

问题:如果"错误的结果" ,我无法理解发生了什么。我会说,它应该返回与"正确结果" 相同的结果。你能帮我意识到它有什么问题吗?

错误的结果

>>> Frame.objects.all().exclude(item__lost_day__isnull=True)
    <QuerySet [<Frame: 3>]>

正确的结果:

>>> Frame.objects.all().filter(item__lost_day__isnull=False)
    <QuerySet [<Frame: 1>, <Frame: 3>]>

自我检查

>>> a = Item.objects.get(pk=1)
>>> a.lost_day
datetime.date(1997, 1, 1)
>>> a.lost_day is None
False

>>> b = Item.objects.get(pk=2)
>>> b.lost_day
datetime.date(1997, 2, 2)
>>> b.lost_day is None
False

models.py

class Frame(models.Model):
    pass

class Item(models.Model):
    frame = models.ForeignKey(Frame,
                          blank=False,
                          on_delete=models.PROTECT,
                          verbose_name=_("frame"))
    lost_day = models.DateField(auto_now=False,
                                auto_now_add=False,
                                blank=True,
                                null=True,
                                verbose_name=_("lost"))

1 个答案:

答案 0 :(得分:0)

你能表明:

Frame.objects.filter(pk=1).values('item__lost_day')

看起来你有多个引用为空而不是lost_day,所以我们有

[{'item__lost_day': None},
 {'item__lost_day': datetime.date(1997, 1, 1)},
 {'item__lost_day': None}]

当您查询Frame.objects.exclude(item__lost_day__isnull=True)时,djanqo会获取所有frames没有item__lost_day__isnull的{​​{1}}这是pk=3帧,但它有空值,但不是frame <1> < / p>

当你Frame.objects.filter(item__lost_day__isnull=False)时,django会发现所有frames都不是lost_day,而且他们是1和3 ==好吧。

你的研究中最麻烦的是你改变条件(null,not_null)和方法(过滤,排除)一起