更新子类中的父dict

时间:2017-02-13 16:56:45

标签: python python-3.x class metaclass

我有这样的课程:

Public Sub Main()

        ' Get the unmanaged connection object, from the connection manager called "HTTP Connection Manager"
        Dim nativeObject As Object = Dts.Connections("HTTP_FileName").AcquireConnection(Nothing)

        ' Create a new HTTP client connection
        Dim connection As New HttpClientConnection(nativeObject)



        ' Download the file #1
        ' Save the file from the connection manager to the local path specified
        Dim filename As String = "DestinationPath"
        connection.DownloadFile(filename, True)

        Dts.TaskResult = ScriptResults.Success
    End Sub

当我创建子类时,我希望将class Parent(object): _defaults = { 'key': 'value', 'key2': 'value', } class Child(Parent): _defaults = { 'key2': 'value2', 'key3': 'value2', } 设置为父类_defaults,然后使用子_defaults进行更新。所以实际解析的类应该如下所示:

_defaults

使用class Child(object): _defaults = { 'key': 'value', 'key2': 'value2', 'key3': 'value2', } 构造函数还是可以吗?

3 个答案:

答案 0 :(得分:2)

您可以使用collections.ChainMap

完成此操作
import collections

class Child(Parent):
    _defaults = collections.ChainMap({
        'key2': 'value2',
        'key3': 'value2',
    }, Parent._defaults)

当然,你可以编写一个元类来为你组合这些东西,但要弄清楚(一般来说)哪些地图与之相结合将会很棘手超类上的地图,应该覆盖......

答案 1 :(得分:1)

直接阅读字典项目,然后更新?

class Parent(object):
    _defaults = {
        'key': 'value',
        'key2': 'value',
    }


class Child(Parent):
    _defaults = {k: v for k, v in Parent._defaults.items()}
    _defaults.update({'key2': 'value2',
                      'key3': 'value2'})


testpar = Parent()
test = Child()

print(testpar._defaults)
print(test._defaults)

打印:

{'key2': 'value', 'key': 'value'}
{'key3': 'value2', 'key2': 'value2', 'key': 'value'}

2.7和3.5

答案 2 :(得分:1)

使用元类,您需要在__new__方法中执行此操作,以便在实例化之前应用更改。由于__new__方法接受cls, name, bases, namespace, **kwds作为参数,您可以使用bases参数访问父对象,该参数是所有基类的元组,然后您可以简单地更新您的预期属性。

class MyMetaClass(type):

    def __new__(cls, name, bases, namespace, **kwds):
        bases[0]._defaults.update(namespace['_defaults'])
        result = type.__new__(cls, name, bases, dict(namespace))
        return result


class Parent(object):
    _defaults = {
        'key': 'value',
        'key2': 'value',
    }

class Child(Parent, metaclass=MyMetaClass):
    _defaults = {
        'key2': 'value2',
        'key3': 'value2',
    }

演示:

c = Child()    
print(type(c).__bases__[0]._defaults)
{'key2': 'value2', 'key3': 'value2', 'key': 'value'}

请注意,正如@jsbueno所提到的,此方法存在一个很大的问题,即在每个实例化时更新父类的_defaults属性。拒绝此问题的一种方法可能是为元类提供一个标志,以便仅更新父类一次。