Python defaultdict类实例化与默认值

时间:2018-12-13 11:56:09

标签: python class instantiation defaultdict

将defaultdict配置为实例化一个类时,如果该类具有默认参数,则行为会有所不同。

例如,这是预期的行为:

from typing import List
from collections import defaultdict

class Test:
    def __init__(self):
        self.values = []

tests = defaultdict(Test)

tests['a'].values.append(1)
tests['b'].values.append(2)

print([f"{id}: {t.values}" for id, t in tests.items()]) #--> ['a: [1]', 'b: [2]']

现在,当类具有默认值时,所有对象共享相同的引用:

class Test:
    def __init__(self, values = []):
        self.values = values

tests = defaultdict(Test)

tests['a'].values.append(1)
tests['b'].values.append(2)

print([f"{id}: {t.values}" for id, t in tests.items()]) #--> ['a: [1, 2]', 'b: [1, 2]']

仅当参数是引用时,才会发生这种情况,例如:

class Test:
    def __init__(self, values = 0):
        self.values = values

tests = defaultdict(Test)

tests['a'].values += 1
tests['b'].values += 1

print([f"{id}: {t.values}" for id, t in tests.items()]) #--> ['a: 1', 'b: 1']

那是为什么?

1 个答案:

答案 0 :(得分:1)

之所以会发生这种情况,是因为在定义函数时,默认值会被精确地评估一次,而不是每次调用时都会被评估。

https://docs.python-guide.org/writing/gotchas/#mutable-default-arguments

并且要澄清的是,python中的所有var都是引用。只是它们所指的某些东西是可变的,而有些不是。