python 杂记3

__slots__:

Python是动态语言  ,于是当我们定义了一个class之后 创建一个class的实例后 我们可以给改实例绑定任何属性和方法

>>> class Student(object):
pass
>>>s=Student()
>>>s.name='lc'#动态给实例绑定一个属性
>>>print s.name
lc

同样还可以给一个实例绑定一个方法

>>> def set_age(self,age):
self.age=age
>>>from types import MethodType
>>>s.set_age=MethodType(set_age,s,Student)
>>>s.set_age(25)
>>>s.age
25

但是这样绑定 在另一个实例上是不起作用的 因此需要将其绑定在 Student上

>>> def set_score(self,score):
self.score=score
>>>Student.set_score=MethondType(set_score,None,Student)
 __slots__ :

变量  这个变量用来限制这个class能够添加的属性

>>> class Student(object):
__slots__=('name','age')

这样除了name和age 这两个属性外 不能再绑定其他的属性 ,但是需要注意的是 __slots__这个变量只对当前的类起作用 不对子类起作用

 @property

相当于装饰器  负责把一个方法变成属性调用。

              
>>> class Student(object):
@property
def score(self):
return self.score
@score.setter
def score(self,value):
if not isinstance(value,int):
raise ValueError('must be a integer')
if value<0 or value>100:
raise ValueError('0-100')
self.score=value
>>> s=Student()
>>> s.score=60 #OK
>>> s.score
60
>>>s.score=9999
Traceback........
ValueRrror:0-100

 @property 把一个getter方法变成属性  然后又创建了@score.setter 负责把一个setter方法变成属性赋值   如果没有@score.setter 方法 则这个属性就是只读的属性

 __iter__().

如果想要被for...in循环遍历 就必须实现 __iter__()这个方法 该方法返回一个迭代对象  Python for 循环就会不断调用迭代对象的next()方法拿到下一个值 直到遇到StopIteration 异常

>>> class Fib(objcet):
def __init__(self):
self.a,self.b=0,1#初始化两个计数器a和b
def __iter__(self):
return self #实例本是就是迭代对象 故返回自己
def next(self):
self.a,self.b=self.b,self.a+self.b #计算下一个值
if self.a>100000:#退出循环条件
raise StopIteration()
return self.a #返回下一个值
>>> for i in Fib():
print i
1
1
2
.......

 __getitem__

上述实例 Fib 虽然能过用于for...in 循环 但是却没有办法像list那样按照下标取元素  这就需要用到 __getitem__()方法:

                      
>>> class Fib(object):
def __getitem__(self,n):
a,b=1,1
for x in range(n):
a,b=b,a+b
return a
>>> f=Fib()
>>> f[0]
1
>>> f[3]
3

 但是这样 对于 切片却不可用 原因是 切片传入的是切片对象 slice

>>> class Fib(object):
def __getitem__(self,n):
if isinstance(n,int):
a,b=1,1
for x in range(n):
a,b=b,a+b
return a
if isinstance(n,slice):
start=n.start
stop=n.stop
a,b=1,1
L=[]
for x in range(stop):
if x>=start:
L.append(a)
a,b=b,a+b
return L
>>> f=Fib()
>>> f[0:5]
[1,1,2,3,5]

这样就实现了切片  但是没有对step的处理 也没有负数的处理

__getattr__()

本来如果调用了对象不存在的属性就会报错 但是 写上 __getattr__()之后 解释器就会尝试从这个方法中获得属性的值

>>> class Student(object):
def __init__(self):
self.name='lc'
def __getattr()__(self,attr):
if attr=='score':
return 99
raise AttributeErrors('has no this attr')
>>> s = Student()
>>> s.score
99

 __call__() :
让对象本身相当于一个方法一样被调用
                      
>>> class Student(object):
def __init__(self,name):
self.name=name
def __call__(self):
print self.name
>>> s=Student('lc')
>>> s()
lc
__call()__还可以定义参数  这样就可以把对象像一个函数一样调用  Callable() 函数可以判断一个对象是否可以被调用。


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值