为什么Python的copy.copy()返回的对象不等于原始对象?

Neo*_*ang 6 python copy

在Python中,如果我复制列表或字典,则复制的实例等于原始实例:

>>> a = [1, 2, 3]
>>> b = copy.copy(a)
>>> a == b
True
>>> a = {"a":1, "b":2}
>>> b = copy.copy(a)
>>> a == b
True
Run Code Online (Sandbox Code Playgroud)

但是如果我复制一个对象,结果就不等于原始对象:

>>> class MyClass():
...     def __init__(self, name):
...             self._name= name
...
>>> a = MyClass('a')
>>> b = copy.copy(a)
>>> a == b
False
Run Code Online (Sandbox Code Playgroud)

为什么?

Ana*_*mar 6

通过调用__eq__()函数来检查Python中对象的相等性.

例:

>>> class CA:
...     def __eq__(self, other):
...             print("Equals")
...             return True
...
>>> c = CA()
>>> b = CA()
>>> c == b
Equals
True
Run Code Online (Sandbox Code Playgroud)

这是因为list相等性取决于元素,而不是存储列表的实际内存位置(引用),也就是说,它们可以是两个不同的列表引用,但如果它们具有相同顺序的相同元素,则列表是等于.

例:

>>> l = [1,2]
>>> l1 = [1,2]
>>> id(l)
2830504
>>> id(l1)
2831864
>>> l == l1
True
Run Code Online (Sandbox Code Playgroud)

但是自定义类,你没有被覆盖__eq__(),因此它将调用__eq__()父类,它是object,并根据引用检查相等性.

当你这样做时,copy.copy()它会进行浅层复制,也就是说,它会创建一个新实例,该对象的所有成员(属性等)保持不变.因此,它们是不相等的(因为它们是不同的参考/不同的实例).

如果您希望MyClass基于此检查相等性self._name,则必须覆盖该__eq__()功能.

您可以在此处找到有关比较的更多信息.