2

|运算符有两种神奇的方法,正常和反射。

# object + other
__or__(self, other)
    # Implements bitwise or using the | operator.

# other + object
__ror__(self, other)
    # Implements reflected bitwise or using the | operator.

in运算符只有一种魔术方法。

# item in object
__contains__(self, item)
    # __contains__ defines behavior for membership tests using in and not in.

如何实现in运算符反射魔术方法?

# object in sequence
__rcontains__(self, sequence):
    # defines behavior for self in or not in sequence

当你想实现 sql 条件时它会很有用

class Field(object):
    def __lt__(self, other):
        return '<', self._value, other

Model.objects.filter(Field('a') > 1)
Model.objects.filter(Field('a') in [1, 2, 3, 4])
4

1 回答 1

2

你不能,因为in运算符在语义上与一个对象“包含”另一个对象的含义的定义相关联。所以操作必须在容器类中定义(这里是list),而不是值(Field)。

为了说明,in在你的情况下是这样使用的:

Field('a') in [Field('a'), Field('b'), Field('c')]

这当然不是你想要的。

正如您在评论中提到的那样,您在这里最接近您想要的东西是使用 Djangofieldname__in==[1, 2, 3, 4]或 SQLAlchemy 之类的东西Table.fieldname.in_([1, 2, 3, 4])。例如,您可以将方法添加到Field

Field('a').is_in([1, 2, 3])

另一种方法是创建一个特定的容器类,以便您可以编写:

Field('a') in Values([1, 2, 3])

但它不仅更冗长(需要额外的导入),而且我认为更难理解背后真正发生的事情。

这也可以:

Field('a') == [1, 2, 3]

但同样,它感觉更“神奇”和令人困惑,因为它不尊重==.

于 2018-06-02T11:10:41.173 回答