Python中的元类

类的创建

class myType(type):
    # new,init 创建类时调用
    def __new__(self,  *args, **kwargs):
        print('myType__new__')
        new_cls = super().__new__(self, *args, **kwargs)
        return new_cls
    def __init__(self,  *args, **kwargs):
    	print('myType__init__')
        super().__init__( *args, **kwargs)
        self.instance = None

    # 创建对象时调用call
    def __call__(self, *args, **kwargs):
       # 1 调用你自己的类的__new__方法去创建对象
        empty_data = self.__new__(self, *args, **kwargs)

        # 2 调用你自己类的__init__方法去初始化
        self.__init__(self, *args, **kwargs)

        return empty_data


class Foo(metaclass=myType):
    def __init__(self, name):
        print('foo__init')
        self.name = name
    def __new__(self, *args, **kwargs):
        print('foo__new')
        return self
    def __call__(self, *args, **kwargs):
        print('foo__call__')

简单明了,Foo类由myType进行创建,运行结果如下

myType__new__
myType__init__

说明: 类的创建所执行的顺序是1.new 2.init
当创建Foo对象时( Foo( ) ),将会执行元类中的 call, 而 call 中所调用的self.__new__和self.__init__将会调用类Foo中的进行初始化,相关代码如下:

Foo('name')

运行结果:

myType__new__
myType__init__
foo__new
foo__init

不难看出,类的创建由元类 myType 创建,而类的实例化则由 call 去操作,根据以上内容,我们可以自己设计一个单例模式,代码如下:


class myType(type):
    # new,init 创建类时调用
    def __new__(self,  *args, **kwargs):
        new_cls = super().__new__(self, *args, **kwargs)
        return new_cls
    def __init__(self,  *args, **kwargs):
        super().__init__( *args, **kwargs)
        self.instance = None

    # 创建对象时调用call
    def __call__(self, *args, **kwargs):
        if self.instance is None:
            # 1 调用你自己的类的__new__方法去创建对象
            self.instance = self.__new__(self, *args, **kwargs)

        # 2 调用你自己类的__init__方法去初始化
        self.__init__(self.instance, *args, **kwargs)

        return self.instance


class Foo(metaclass=myType):
    def __init__(self, name):
        print('foo__init')
        self.name = name
    #
    def __new__(self, *args, **kwargs):
        print('foo__new')
        return self
    #
    def __call__(self, *args, **kwargs):
        print('foo__call__')

fo = Foo('foooooo')
fo2 = Foo('fooooooo1')
print(fo.name)
print(fo2.name)
print(id(fo))
print(id(fo2))

代码解释:在元类中,初始化一个标记,通过观察标记是否存在来判断是否已经被实例化过,若未实例化,则通过调用Foo中的new方法返回一个对象,然后进行初始化,从而得到一个类的实例,当该类被实例化过一次之后,再次调用Foo类进行创建实例,元类发现后将会返回第一次创建的实例,代码运行结果如下:

foo__new
foo__init
foo__init
fooooooo1
fooooooo1
5039529872
5039529872
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值