class Open:
def __init__(self,name):
self.name = name
def __enter__(self):
pass
def __exit__(self, exc_type, exc_val, exc_tb):
pass
return True #如果返回True 程序运行过程中发生异常也会被吞掉
with Open('a.txt') as f: #f是一个对象 触发__enter__
print(f.name) #如果这里发生异常,则也会触发__exit__
print('=====》') #这里执行后会触发__exit__
描述符应用:检测类型
至少实现__get__、__set__、__delete__中的一个方法
class Typed:
def __init__(self,key,expected_type):
self.key = key
self.expected_type = expected_type
def __get__(self, instance, owner):
return isinstance.__dict__[self.key]
def __set__(self, instance, value): #instance代表被代理的字典,这里就是People的字典
if not isinstance(value,self.expected_type):
raise TypeError('不是%s,类型错误喔' %self.expected_type) #类型不对,抛出异常,终止程序
instance.__dict__[self.key] = value
def __delete__(self, instance):
isinstance.__dict__.pop(self.key)
class People:
name = Typed('name',str) #属性name被Typed代理了(如果代理没生效,注意描述符的优先级)
age = Typed('age',int)
def __init__(self,name,age,salary):
self.name = name
self.age = age
self.salary = salary
# people = People(1111,23,100000)
people = People('lin',23,100000)
print(people.__dict__)
类的装饰器的基本原理
def Typed(**kwargs):
def deco(obj):
for key,val in kwargs.items():
# obj.__dict__[key] = val
setattr(obj,key,val)
return obj
return deco
@Typed(x = 1,y = 2, z = 3)
class Foo:
pass
f = Foo
print(Foo.__dict__)
类的装饰器的应用
class Typed:
def __init__(self,key,expected_type):
self.key = key
self.expected_type = expected_type
def __get__(self, instance, owner):
return isinstance.__dict__[self.key]
def __set__(self, instance, value): #instance代表被代理的字典,这里就是People的字典
if not isinstance(value,self.expected_type):
raise TypeError('不是%s,类型错误喔' %self.expected_type) #类型不对,抛出异常,终止程序
instance.__dict__[self.key] = value
def __delete__(self, instance):
isinstance.__dict__.pop(self.key)
def deco(**kwargs):
def wrapper(obj):
for key,val in kwargs.items():
setattr(obj,key,Typed(key,val))
return obj
return wrapper
@deco(name = str,age = int,salary = float)
class People:
def __init__(self,name,age,salary):
self.name = name
self.age = age
self.salary = salary
people = People('lin',23,10000.1)
print(People.__dict__)
自定制property
class Lazyproperty:
def __init__(self,func):
self.func = func
def __get__(self, instance, owner):
return self.func(instance)
def __set__(self, instance, value):
pass
def __delete__(self, instance):
pass
class Room:
area = Lazyproperty('x') #描述符
def __init__(self,name,width,length):
self.name = name
self.width = width
self.length = length
# @property #area = property(area) property:
@Lazyproperty #area = Lazyproperty(area)
def area(self):
return self.width * self.length
room = Room('卧室',10,10)
print(room.area) #实例调用
print(Room.area) #类调用
自定制property实现延迟计算功能
class Lazyproperty:
def __init__(self,func):
self.func = func
def __get__(self, instance, owner):
if instance is None:
return self
res = self.func(instance)
setattr(instance,self.func.__name__,res) #实现缓存效果 把结果存起来,下次直接取缓存的
return res
def __set__(self, instance, value):
pass
def __delete__(self, instance):
pass
class Room:
area = Lazyproperty('x') #描述符
def __init__(self,name,width,length):
self.name = name
self.width = width
self.length = length
# @property #area = property(area) property:
@Lazyproperty #area = Lazyproperty(area)
def area(self):
return self.width * self.length
room = Room('卧室',10,10)
print(room.area) #实例调用
自定制property 补充
class ClassMethod:
def __init__(self,func):
self.func = func
def __get__(self, instance, owner):
def feedback(*args,**kwargs):
# print('在这里可以加功能........')
return self.func(owner,*args,**kwargs)
return feedback
class People:
name = 'lin'
@ClassMethod
def say_hi(self,msg):
print('你好啊 %s %s' %(self.name,msg))
People.say_hi('你是谁')
people = People()
people.say_hi('你是谁')
class Foo:
@property
def test(self):
print('get的时候运行了喔')
@test.setter
def test(self,val):
print('set设置参数',val)
@test.deleter
def test(self):
print('delete的时候运行了喔')
f = Foo()
f.test
f.test = 1
class Foo:
def get_test(self):
print('get的时候运行了喔')
def set_test(self, val):
print('set设置参数', val)
def del_test(self):
print('delete的时候运行了喔')
test = property(get_test, set_test, del_test)
f = Foo()
f.test
f.test = 1
class Goods:
def __init__(self):
self.original_proice = 100
self.discount = 0.8
@property
def price(self):
new_price = self.original_proice * self.discount
return new_price
@price.setter
def price(self,value):
self.original_proice = value
@price.deleter
def price(self):
del self.original_proice
goods = Goods()
print(goods.price)
goods.price = 200
print(goods.price)
元类介绍:类的类
class Foo:
pass
FFo = type('FFo',(object,),{'x':1,'__init__':'__init__'})
print(Foo)
print(FFo)
print(FFo.__dict__)
自定义元类
class MyType(type):
def __init__(self,a,b,c):
print('元类的构造函数')
def __call__(self, *args, **kwargs):
print('============》')
print(self)
print(args,kwargs)
obj = object.__new__(self) #object.__new__(Foo) 得到foo
self.__init__(obj,*args,**kwargs) #Foo.__init__()
return obj
class Foo(metaclass = MyType): #Foo = MyType(Foo,'Foo',(),{})
def __init__(self,name):
self.name = name
foo = Foo('lin')
print(foo)
print(foo.__dict__)