元类 metaclass

metaclass

  • 类由Type创建
  • 对象由创建

MetaClass作用

用来指定当前类由谁来创建(默认type创建)。

MetaClass 会被继承,如果父类指定了元类,那么子类也是由这个元类创建

class MyType(type):
    def __init__(self, *args, **kwargs):
        print('init')
        super(MyType, self).__init__(*args, **kwargs)

    def __call__(self, *args, **kwargs):
        print('call本质:调用类的__new__,再调用类的__init__')
        return super(MyType, self).__call__(*args, **kwargs)


class Foo(metaclass=MyType):
    pass


class Bar(Foo):
    pass


obj = Bar()

# init
# init
# call本质:调用类的__new__,再调用类的__init__

  

1. 创建类的两种方法

#class创建

class Foo(object):
    pass

#type创建

#运用type创建类、添加属性
# type(类名,(继承的类),{属性和方法,用键值对的方式})
Test = type("Test",(),{'age':13,'name':"wangbo"})
test = Test()
print(test.age) #13
#利用type添加方法
@classmethod #类方法
def testClass(cls):
    print(cls.name)

@staticmethod #静态方法
def testStatic():
    print("static method.....")

def echo_age(self):
    print(self.age)
#
Test2 = type("Test2",(Test,),{'echo_age':echo_age,'testStatic':testStatic,'testClass':testClass})
test2 = Test2()
test2.echo_age()
test2.testStatic()
test2.testClass()

2. 调用顺序

class MyType(type):
    def __init__(self, *args, **kwargs):
        print("元类init")
        super(MyType, self).__init__(*args, **kwargs)

    def __new__(cls, *args, **kwargs):
        print("new")
        return super().__new__(cls, *args, **kwargs)

    def __call__(self, *args, **kwargs):
        print("call")
        obj = self.__new__(self, *args, **kwargs)  # object.__init__(....)
        obj.__init__(*args, **kwargs)
        # self.__init__(obj,*args, **kwargs)
        return obj


class Foo(object, metaclass=MyType):
    def __init__(self):
        print('本类init')

x = Foo()


# new
# 元类init
# call
# 本类init


# 调用顺序:创建一个类调时候先调用他元类的__new__,然后元类的__init__,实例化这个类的时候调用元类的__call__,
#         在__call__中调用这个类的__new__然后__init__得到一个对象
# 类是Mytype的对象,实例化时加括号调用__call__

3. 设置元类

py3
class Foo(object,metaclass=MyType):
    pass 

py2        
class Foo(object):
    __metaclass__ = MyType
原文地址:https://www.cnblogs.com/zhoujunhao/p/8585283.html