Python中的None与identity相同

16 python coding-style

各种Python指南说使用x is None而不是x == None.这是为什么?等式用于比较值,因此看起来是否x具有值None表示是否自然,用==和不用表示is.有人可以解释为什么is是首选形式,并显示一个例子,其中两个不给出相同的答案?

谢谢.

Die*_*Epp 14

人们使用的原因is是因为使用没有优势==.可以编写比较相等的对象None,但这种情况并不常见.

class A(object):
    def __eq__(self, other):
        return True

print A() == None
Run Code Online (Sandbox Code Playgroud)

输出:

True
Run Code Online (Sandbox Code Playgroud)

is运营商也快,但我不认为这确实非常重要.

  • @ user248237`is`运算符可能更快,因为它不能被重载 - 没有相当于'a == b`可能产生的调用链(通常:`a .__ eq __(b)`,`b .__ eq __(a)`最后`a是b` - 第一个返回"NotImplemented"以外的东西获胜.`is`只测试一件事,Python直接知道,并且总是在一次测试后给你一个答案."无"是无价值的,但你可以把它想象成一个空的C指针 - 一个指针的值就是它所指向的,一个空指针指向什么都没有. (5认同)
  • 我想你还可以补充说,只有一个`None`对象,它没有任何价值.因为所有`None`s都是同一个对象,所以你应该使用对象标识运算符`is`.比较运算符`==`是不合适的,因为`None`没有值. (3认同)
  • @Hamish在什么意义上它"没有价值"?它*是一个值,就像每个其他对象一样. (3认同)
  • @ user248237但重要的是``是None`和`is not None'确切地说出你的意思 - 正如DietrichEpp所指出的那样,*可能*可以重载`x == None`以返回True为非-`None``x`,可能是通过一个bug.`is`意味着平等(通常,对于唯一的反例,请参见`float('nan')`,但是即使与单身人士进行比较,平等并不总是意味着身份(你需要LHS上的单身人士,才能拥有`__eq__` do`返回self是other`,并且不将它与它的子类进行比较).`是`说出你的意思 - 比规则容易得多. (3认同)

Gre*_* E. 11

is关键字测试身份.它不是一个比较运算符==.使用is不只是测试两个参数是否具有相同的值和/或相同的内部结构:即,它测试这两个参数是否实际引用内存中的同一对象.这有很多含义,其中一个是is无法重载,另一个是可变类型和不可变类型之间的行为不同.例如,请考虑以下事项:

>>> l1 = range(5)
>>> l2 = range(5)
>>> l1 == l2
True
>>> l1 is l2
False
>>> l3 = l1
>>> l1 is l3
True
>>> s1 = "abcde"
>>> s2 = "abcde"
>>> s1 == s2
True
>>> s1 is s2
True
Run Code Online (Sandbox Code Playgroud)

在这里,由于列表是可变的,他们不能共享内存中的位置,并因此is==产生不一致的结果.另一方面,字符串是不可变的,因此在某些情况下可以合并它们的存储器.基本上,is只能可靠地用于简单的,不可变的类型,或者在多个名称指向内存中完全相同的对象的情况下(例如l3上面示例中的使用),并且它的使用表明需要测试身份而不是值.我希望is稍微快一点,==因为它不执行方法查找,但我可能会弄错.当然,对于像列表或dicts这样的复杂容器对象,is应该比==(O(1)vs O(n)快得多(大概).也就是说,速度问题大多是一个没有实际意义的问题,因为这两者不应该被认为是可以互换的.