提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档
文章目录
目录
一.元类的定义
1.什么是元类
- 元类是类的类,用来加工类,创建类
- 实例是类创建的,而类是元类创建的
- 类里面的mateclass为默认值,表明类是type创建的
class Person:
pass
print(type(Person)) # 输出: <class 'type'>
这里我们会发现Person的类型是type
2.type的用法
type本身也是一个函数,用来创建动态类,他的语法是
type(类名, 父类元组, 属性字典)
我们来动态创建一个类
#第一个参数是类名
# #第二个是父类列表
# #第三个参数是类里面的属性
def __init__(name):
return name
Myclass = type('Person',(object,),{'__doc__':'通过手动创建',
'info':'两讲授','__init__':__init__})
三、元类工作流程
接下来的一段代码,会告诉你元类是如何创建类的
class MyType(type):#这里不写也默认有一个type,因为所有类都是type类型
def __new__(cls, name,bases,dic):
instance = super().__new__(cls,name,bases,dic)
print(id(instance))# 1886804883152
return instance
class People(metaclass=MyType):#表明这个是由Mytype类创建
pass
print(id(People))# 1886804883152
具体流程:
- 定义了一个类并且指向了metaclass = Mytype,则MyType会自动帮你创建这个类
- MyType调用父类的__new__创建对象
- 调用父类的__init__初始化对象
- 返回类对象
四、使用元类加工一个类
# 加工类
class A:
pass
class MyType(type):
def __new__(cls, name,bases,dic):
# print(name,bases,dic)
#更改类名
name = 'My' + name
#添加父类
bases = list(bases)
bases.append(A)
bases = tuple(bases)
#将类方法中的大写改为小写
temp = {}
for k ,v in dic.items():
if not k.startswith("__"):
temp[k.lower()] = v
else:
temp[k] = v
instance = super().__new__(cls,name,bases,temp)
print(name,bases,temp)
return instance
class People(metaclass=MyType):
"""注释"""
INFO = "梁教授"
print(id(People),People.__name__)
p = People()
# print(p,id(p))
通过对类的加工,我们给People类增加了父类A,我们将People中属性INFO改为了合法的info,同时我们将People的名字改为了MyPeople
五、单例类
Python编程中,单例模式是一种常见的设计模式,是为了防止一个实例被多次创建,只允许实例化一次,应用场景有数据库连接池,日志记录器,管理类等
1.单例类实现方式
1.1.使用__new__方法创建
__new__是用来创建实例的特殊方法,在init之前被调用
class Singleton:
def __new__(cls, *args, **kwargs):
if not hasattr(cls,'instance'):
instance = super().__new__(cls)
print(id(instance))
setattr(cls,'instance',instance)
return getattr(cls,'instance')
s = Singleton()
s1 = Singleton()
print(s is s1)
# 输出
# 2544341119536
# True
1.2.使用元类创建单例
class Singleton(type):
instance = {}
def __call__(cls, *args, **kwargs):
#当类被调用时,就会触发__call__方法
if cls not in cls.instance:
cls.instance[cls] = super().__call__(*args,*kwargs)
return cls.instance[cls]
class SingletonManage(metaclass=Singleton):
pass
s = SingletonManage()
s1 = SingletonManage()
print(s is s1)#True

172

被折叠的 条评论
为什么被折叠?



