更改字典时避免使用Python中的deepcopy()

2024-05-23 16:03:05 发布

您现在位置:Python中文网/ 问答频道 /正文

我正在寻找一种解决方案,以避免在使用Python的任务中使用deepcopy()。在

我正在使用chu-liu-edmonds算法实现一个统计依赖性解析器。我有一个用字典表示的图,每个头节点都存储为一个键,每个节点都有一个包含一个或多个类arc对象的列表作为值。在

在cle算法中,我需要修改图(收缩一个循环)。这意味着,我需要删除弧对象和弧头,并添加其他对象,而我稍后需要原始图形来扩展那些收缩的循环。现在,我通过深度复制原始图形并将其传递给contract函数来实现这一点。在

现在我用cProfile运行我的程序,发现deepcopy的所有操作都是算法中花费时间最多的部分。在

所以我的问题是:在我的情况下,有没有办法避免/减少这种情况?在


Tags: 对象算法解析器图形列表字典节点情况
2条回答

更新: 如果您想更改dict中的列表,您无法避免deepcopy(),但您应该执行以下操作:

“保存”只保存图的可变/可删除元素(即列表)的值,完整图。然后对dict/graph进行所需的修改,然后可以使用“saved”元素进一步修改graph。在

使用dict.copy(),如下所示,d.copy()的速度快了100000倍:

from copy import deepcopy
from time import time

# with simply assignment       -

d = {"a":[x for x in range(1000000)]}

t = time()
e = d
print 'elapsed time with standard assignment:', time()-t

e["b"] = [1,2,3]
del e["a"]
print d.keys()

# with deepcopy()           

d = {"a":[x for x in range(1000000)]}

t = time()
e = deepcopy(d)
print '\nelapsed time with deepcopy():', time()-t

e["b"] = [1,2,3]
del e["a"]
print d.keys()

# with d.copy()           -

d = {"a":[x for x in range(1000000)]}

t = time()
e = d.copy()
print '\nelapsed time with d.copy():', time()-t

e["b"] = [1,2,3]
del e["a"]
print d.keys()

输出:

^{pr2}$

正如@dmargol1在评论中建议的那样,我可以避免deepcopy()和copy(),而是从头开始构建图形,而不是复制和修改它,这实际上要快得多。在

如果可能的话:去做!在

如果复制是必要的,有两种方法。如果不需要更改值,copy()是一种方法,因为它比deepcopy()快得多(参见@george solymosi的评论)。如果需要更改值,deepcopy是唯一的方法(参见@gall的注释)。在

相关问题 更多 >