首页 > 其他 > 详细

类对象和对象的创建过程分析

时间:2019-08-08 12:07:20      阅读:73      评论:0      收藏:0      [点我收藏+]
  1 #===============================================
  2 class Mymeta(type): #它是个自定制元类了
  3     def __init__(self): #TypeError: __init__() takes 1 positional argument but 4 were given
  4         pass
  5 
  6 class DemoClass(metaclass=Mymeta):
  7     pass
  8 #这个报错是创建类对象DemoClass时,会将类对象的四部分信息传给Mymeta的__init__,但是它只有一个参数,故报错
  9 
 10 #===============================================
 11 class Mymeta(type): #它是个自定制元类了
 12     def __init__(self,name,bases,dict):
 13         print(self)     #self 是DemoClass 类对象
 14         print(type(self))  #self 的类型是Mymeta
 15         print(name)  #类对象名字
 16         print(bases) #类对象继承的基类
 17         print(dict)  #类对象的属性字典
 18 
 19 class DemoClass(metaclass=Mymeta):
 20     pass
 21 输出:
 22     <class __main__.DemoClass>
 23     <class __main__.Mymeta>
 24     DemoClass
 25     ()
 26     {__module__: __main__, __qualname__: DemoClass}
 27 
 28 
 29 #===============================================
 30 class Mymeta(type): #它是个自定制元类了
 31     def __init__(self,*args,**kwargs): #也可以用*args和**kwargs同一接收参数
 32         print(self)
 33         print(args) 
 34         print(kwargs)
 35 class DemoClass(metaclass=Mymeta):
 36     pass
 37 ‘‘‘
 38 <class ‘__main__.DemoClass‘> self
 39 (‘DemoClass‘, (), {‘__qualname__‘: ‘DemoClass‘, ‘__module__‘: ‘__main__‘})
 40 {}
 41 ‘‘‘
 42 #===============================================
 43 此时DemoClass类对象已经创建好了,
 44 如果我们此时执行  DemoClass() 
 45 对象加括号,会调用它的类型中的__call__() 方法,如果它的类中无__call__就会报错:
 46     class Mymeta(type): #它是个自定制元类了
 47         def __init__(self,name,bases,dict):
 48             print("1")
 49 
 50     class DemoClass(metaclass=Mymeta):
 51         def __init__(self,name):
 52             self.name = name
 53 
 54     DemoClass("tom")
 55     没有报错,说明找到了__call__ ,虽然Mymeta中没有,但是在type 中找到了。
 56 #===============================================
 57     class Mymeta(type): #它是个自定制元类了
 58         def __init__(self,name,bases,dict):
 59             print("1")
 60         def __call__(self, *args, **kwargs):
 61             print("2")
 62 
 63 
 64     class DemoClass(metaclass=Mymeta):
 65         def __init__(self,name):
 66             self.name = name
 67 
 68     DemoClass("tom")  #它会调用__call__ 方法
 69     输出: 1,2
 70     现在在Mymeta中找到了__call__,所以就不再去type 中找了,
 71 
 72 #===============================================
 73 其实type 中的__call__是要做三件事的:
 74     创建obj 
 75     然后初始化obj (通过调用它自己的__init__)
 76     然后返回obj 
 77 我们现在在Mymeta中自己的__call__中模拟这个过程:
 78     class Mymeta(type): #它是个自定制元类了
 79         def __init__(self,name,bases,dict):
 80             print("1")
 81         def __call__(self, *args, **kwargs):
 82             print("2")
 83             obj = self.__new__(self)  #类对象DemoClass 调用__new__() ,
 84                 # 首先Mymeta 中没有,于是就去type中找了,那肯定有。然后创建 类对象 (类)的对象
 85             self.__init__(obj,*args,**kwargs) #类对象DemoClass 下的方法
 86             return obj
 87 
 88 
 89     class DemoClass(metaclass=Mymeta):
 90         def __init__(self,name):
 91             self.name = name
 92 
 93     demo = DemoClass("tom")    #它会调用__call__ 方法
 94     print(type(demo))  #返回的是 __new__() 中的参数 即类对象DemoClass
 95 输出是: 
 96     1
 97     2
 98     <class __main__.DemoClass>
 99 
100 #===============================================
101 #demo 对象的name 属性的赋值过程:
102 
103 class Mymeta(type): #它是个自定制元类了
104     def __init__(self,name,bases,dict):
105         print("1")
106     def __call__(self, *args, **kwargs):   #1"tom" 先传到这的args
107         print("2")
108         obj = self.__new__(self) 
109         self.__init__(obj,*args,**kwargs)  #2"tom"再传到这的args
110         return obj   #4带有"tom"属性的obj 返回
111 
112 
113 class DemoClass(metaclass=Mymeta):
114     def __init__(self,name):   #3"tom"最后传到这的name
115         self.name = name
116 
117 demo = DemoClass("tom")    #它会调用__call__ 方法
118 # print(type(demo))  #返回的是 __new__() 中的参数 即类对象DemoClass
119 
120 #===============================================
121 class Mymeta(type): #它是个自定制元类了
122     def __init__(self,name,bases,dict):
123         print("1")
124     def __call__(self, *args, **kwargs):
125         print("2")
126         obj = self.__new__(self)  #Mymeta 中没有,type中有  证明如下: 
127         self.__init__(obj,*args,**kwargs)
128         return obj
129 
130 
131 class DemoClass(metaclass=Mymeta):
132     def __init__(self,name):
133         self.name = name
134 
135 demo = DemoClass("tom")    #它会调用__call__ 方法
136 # print(type(demo))  #返回的是 __new__() 中的参数 即类对象DemoClass
137 print(type.__dict__)
138 
139 type的属性字典:
140 {__subclasscheck__: <method __subclasscheck__ of type objects>, __dir__: <method __dir__ of type objects>, __bases__: <attribute __bases__ of type objects>, __name__: <attribute __name__ of type objects>, __delattr__: <slot wrapper __delattr__ of type objects>, __doc__: <attribute __doc__ of type objects>, __dict__: <attribute __dict__ of type objects>, __base__: <member __base__ of type objects>, __init__: <slot wrapper __init__ of type objects>, __sizeof__: <method __sizeof__ of type objects>, __instancecheck__: <method __instancecheck__ of type objects>, mro: <method mro of type objects>, __subclasses__: <method __subclasses__ of type objects>, __new__: <built-in method __new__ of type object at 0x000000005913DE40>, __qualname__: <attribute __qualname__ of type objects>, __dictoffset__: <member __dictoffset__ of type objects>, __text_signature__: <attribute __text_signature__ of type objects>, __abstractmethods__: <attribute __abstractmethods__ of type objects>, __weakrefoffset__: <member __weakrefoffset__ of type objects>, __setattr__: <slot wrapper __setattr__ of type objects>, __module__: <attribute __module__ of type objects>, __repr__: <slot wrapper __repr__ of type objects>, __itemsize__: <member __itemsize__ of type objects>, __prepare__: <method __prepare__ of type objects>, __call__: <slot wrapper __call__ of type objects>, __getattribute__: <slot wrapper __getattribute__ of type objects>, __flags__: <member __flags__ of type objects>, __basicsize__: <member __basicsize__ of type objects>, __mro__: <member __mro__ of type objects>}
141 从这里可以看到这里有__call__方法和__new__ 方法 
142 
143 这就是类对象和对象的创建过程分析!

 

类对象和对象的创建过程分析

原文:https://www.cnblogs.com/zach0812/p/11319560.html

(0)
(0)
   
举报
评论 一句话评论(0
关于我们 - 联系我们 - 留言反馈 - 联系我们:wmxa8@hotmail.com
© 2014 bubuko.com 版权所有
打开技术之扣,分享程序人生!