替代深度复制python中的点亮BitVectors

时间:2016-10-17 10:21:11

标签: python python-3.x deep-copy

在我的项目中,我使用deepcopy()函数创建一个BitVector列表的深层副本。不幸的是,它花了很多时间。

a = [<BitVector obj at 0x000...>, <BitVector obj at 0x000...>, <BitVector obj at 0x000...> ...]

在更改a时,我不希望b反映更改。

b = deepcopy(a)

但上面的等式花了很多时间。我应该使用哪种替代方案来获得更好的性能?

1 个答案:

答案 0 :(得分:1)

BitVector实现是纯python,可以大大优化复制。此外,所提供的BitVector.deep_copy实现比copy.deepcopy慢得多。这是一个深度拷贝的实现,在我的机器上快了~10倍。

def bitvector_copy(bitvector):
    new = BitVector.__new__(BitVector)
    new.__dict__ = {
        "size": bitvector.size, # size is an int and immutable
        "vector": bitvector.vector[:], # vector is an array, this is enough to get a deepcopy
        # the copy will be disassociated with any file it originated from
        # this emulates how BitVector.deep_copy works
        "filename": None,
        "FILEIN": None,
        "FILEOUT": None
    }
    return new

要复制您的列表,您现在可以:

new_list = [bitvector_copy(vec) for vec in old_list]

对于大多数用例应该足够了。但是,这并不是一个完全深刻的副本。虽然所有新的BitVector都是独立的,但如果列表包含对相同位向量的引用,则会导致问题,例如。

old_list = [BitVector(size=8)] * 2
assert old_list[0] is old_list[1]
new_list = [bitvector_copy(vec) for vec in old_list]
assert new_list[0] is new_list[1] # AssertionError!

通过一些修改,您可以修改复制功能以使用copy.deepcopy并让函数返回真正的深层复制。这确实会减慢复制速度。

def bitvector_deepcopy(self, memo):
    if id(self.vector) in memo:
        vector = memo[id(self.vector)]
    else:
        vector = memo[id(self.vector)] = self.vector[:]
    new = BitVector.__new__(BitVector)
    new.__dict__ = {
        "size": self.size,
        "vector": vector,
        "filename": None,
        "FILEIN": None,
        "FILEOUT": None
    }
    return new
BitVector.__deepcopy__ = bitvector_deepcopy