python中is和==的区别

首先看下面一段程序:
def test():
    # example 1
    a = 'hello'
    b = 'hello'
    print(a is b)  # 输出True
    print(a == b)  # 输出True
    
    # example 2
    a = 'hello world'
    b = 'hello world'
    print(a is b)  # 输出False
    print(a == b)  # 输出True
    
    # example 3
    a = [1, 2, 3]  
    b = a
    print(a is b)  # 输出True
    print(a == b)  # 输出True

上面的输出结果为什么有的相同,有的不相同呢?

官方文档描述is为对象标示符(object identity),而==表示的是相等。is的作用是用来检查对象的标示符是否一致,也就是两个对象在内存中的位置是否一样,而==是用来检查两个对象是否相等。

我们来看一下下面的程序,检查每个对象的id

def test():
    # example 1
    a = 'hello'
    b = 'hello'
    print(id(a))   # 输出2378974396344
    print(id(b))   # 输出2378974396344
    print(a is b)  # 输出True
    print(a == b)  # 输出True
    
    # example 2
    a = 'hello world'
    b = 'hello world'
    print(id(a))   # 输出2378974396344
    print(id(b))   # 输出2033022437424
    print(a is b)  # 输出False
    print(a == b)  # 输出True
    
    # example 3
    a = [1, 2, 3]  
    b = a
    print(id(a))   # 输出1641701071688 
    print(id(b))   # 输出1641701071688 
    print(a is b)  # 输出True
    print(a == b)  # 输出True

打印出id结果就很清晰了,只要a和b值相同,==结果输出True;只有id相同,is结果输出True。但是有一个问题,为什么example1的'hello' a is b就输出True,而example2的'hello world'就输出False。

这是因为前一种情况下Python的字符串驻留机制起了作用。对于较小的字符串,为了提高系统性能Python会保留其值的一个副本,当创建新的字符串的时候直接指向该副本即可。所以'hello'在内存中只有一个副本,a和b的id值相同,而'hello world'是长字符串,不驻留内存,Python中各自创建了对象来表示a和b,所以他们的值相同,但是id值不同。(有些编译器会对程序优化,所以is操作可能不同)。

实际python中None的比较,为什么是is None,而不是== None呢?

这是因为None在Python里是个单例对象,一个变量如果是None,它一定和None指向同一个内存地址。而==None背后调用的是__eq__,而__eq__可以被重载,下面是一个is not None但== None的例子

class Foo(object):
        def __eq__(self,other):
            return True
    f = Foo()
    print(f is None)  # 输出False
    print(f == None)  # 输出True
上面==被重载,所以输出True。


猜你喜欢

转载自blog.csdn.net/legend_hua/article/details/80080132