python - Python - 复制包含类对象数组B的类对象A的正确方法是什么
问题描述
我想复制一个类对象数组并更新原始数组而不改变复制的数组。请参阅说明问题的此代码。当我改变 A 时,我不希望 B 改变:
复制类对象数组测试
import copy
class B:
val=0
p=40
class A:
g=[]
def __init__(self):
self.g.append(B())
self.g.append(B())
def main():
a=A()
print("a.g[0] is " + str(a.g[0].val) + " , " + str(a.g[0].p))
print("a.g[1] is " + str(a.g[1].val) + " , " + str(a.g[1].p))
print("Copying a to b")
b=copy.deepcopy(a)
print ("Now updating a[0]")
a.g[0].val=25
print("a.g[0] now is " + str(a.g[0].val) + " , " + str(a.g[0].p))
print("a.g[1] now is " + str(a.g[1].val) + " , " + str(a.g[1].p))
print("Now printing which which was copied from original a")
print("b.g[0] is " + str(b.g[0].val) + " , " + str(b.g[0].p))
print("b.g[1] is " + str(b.g[1].val) + " , " + str(b.g[1].p))
if __name__ == "__main__":
main()
解决方案
问题是您通过直接在类中声明它们来将 、 和 定义val
为p
类g
变量。
当您声明一个类变量时,该变量与类本身直接相关并影响该类的所有实例。使用该类的所有对象创建实例变量,但值可能因对象而异。想象一个名为的类wallet
,它有一个名为 的属性money
。每个人都是从金钱wallet
开始1000
的,但他们彼此独立地赚钱和亏钱。如果我将 100 添加到 one wallet
,则所有其他都将更改。类变量的行为不同。假设我给了wallet
一个名为的类变量currency
并将其设置为"USD"
. 如果我将此变量更改为"CAD"
,现在所有wallet
对象的currency
属性都将设置为"CAD"
,包括已经创建的对象。
解决方案是使它们成为实例变量并在下面分配值__init__
而self.<insert>
不是仅仅<insert>
. 您可以在下面看到更改的示例。当我main()
使用对以下类所做的更改运行您的函数时,所做的更改A
未反映在B
.
一个好的经验法则是始终默认在内部声明变量,__init__
因为它会迫使您考虑使用类变量时的行为方式。
class B:
def __init__(self):
self.val=0
self.p=40
class A:
def __init__(self):
self.g=[]
self.g.append(B())
self.g.append(B())
推荐阅读
- php - 无法在 1and1 托管中使用 PHP 会话
- swift - Xcode 编译器错误未在编辑器中突出显示
- intellij-idea - Ktor - 从插件抛出错误快速启动新项目
- python - 如何在 python 中更改 .ttf-Font 字符之间的间距?
- python - 尝试在 python 中使用 smtp 模块使用 Google 服务器向自己发送电子邮件时出现 WinError 10061
- python-3.x - Python 3.7.3 ./configure --with-openssl 找不到 ssl.h
- java - 连接到远程服务器时,我收到警告:找不到合适的证书 - 无需客户端身份验证即可继续
- request - 使用 GitHub GraphQL Api 获得按星级排名的前 10 个 javascript/开源存储库
- android - react-native-media-meta 在调试时工作但在发布 APK 时崩溃
- php - Laravel 5.0 使用自定义 Filsystem 将图像保存为损坏或损坏