Python面向对象之魔法方法
一、简介
python==3.7; 2020-04-12
python 类中,使用左右双下划线的预定义方法。当对对象做某种操作时,会触发魔法方法的调用, 是程序员与Python解释器交互的接口.
二、几个基本的魔法方法
class Constant ( ) :
def __new__ ( cls, * args, ** kwargs) :
print ( f"__new__ 被调用 -- {cls}" )
if not hasattr ( cls, "is_instanced" ) :
cls. is_instanced = super ( Constant, cls) . __new__( cls)
return cls. is_instanced
def __init__ ( self, password) :
print ( f"__init__ 被调用 -- {self}" )
self. password = password
constant = Constant( "123456" )
print ( constant, Constant)
print ( constant. password)
constant = Constant( "111111" )
print ( constant, Constant)
print ( constant. password)
__new__ 被调用 -- <class '__main__.Constant'>
__init__ 被调用 -- <__main__.Constant object at 0x0000027CA719D908>
<__main__.Constant object at 0x0000027CA719D908> <class '__main__.Constant'>
123456
__new__ 被调用 -- <class '__main__.Constant'>
__init__ 被调用 -- <__main__.Constant object at 0x0000027CA719D908>
<__main__.Constant object at 0x0000027CA719D908> <class '__main__.Constant'>
111111
class A ( ) :
def __init__ ( self) :
print ( "init" )
def close ( self) :
print ( "close" )
def __del__ ( self) :
print ( "析构函数被调用" )
self. close( )
a = A( )
print ( "end" )
init
析构函数被调用
close
end
class Fibonacci ( ) :
"""
斐波那契数列1
"""
def __call__ ( self, n) :
self. a = 1
self. b = 1
self. c = 2
if n <= 2 :
return 1
else :
for i in range ( n- 2 ) :
self. c = self. a + self. b
self. a, self. b = self. b, self. c
return self. c
fibonacci = Fibonacci( )
for i in range ( 1 , 11 ) :
print ( fibonacci( i) , end = " " )
1 1 2 3 5 8 13 21 34 55
class Student ( ) :
def __init__ ( self, name, age) :
self. name = name
self. age = age
def __str__ ( self) :
return f"name: {self.name}, age: {self.age}"
class Test ( ) :
name = "Test"
tesla = Student( "Tesla" , 18 )
print ( tesla)
temp = str ( tesla) + f" --- {tesla}"
print ( temp)
test = Test( )
print ( test)
name: Tesla, age: 18
name: Tesla, age: 18 --- name: Tesla, age: 18
<__main__.Test object at 0x0000027CA7657988>
class A ( ) :
"test doc"
name = "name"
a = A( )
a. age = 18
print ( a. __dict__, a. __doc__)
析构函数被调用
close
{'age': 18} test doc
三、 对象属性相关的魔法方法
class Constant ( ) :
def __getattr__ ( self, name) :
print ( "getattr" , name)
def __getattribute__ ( self, name) :
print ( "getattribute" )
return super ( ) . __getattribute__( name)
def __setattr__ ( self, name, value) :
print ( "setattr: " , name, value)
super ( ) . __setattr__( name, value + "--赋值前做点处理" )
def __delattr__ ( self, name) :
print ( "delattr" )
super ( ) . __delattr__( name)
constant = Constant( )
constant. user = "Tesla"
print ( "打印 user: " , constant. user)
del constant. user
print ( "打印 user: " , constant. user)
setattr: user Tesla
getattribute
打印 user: Tesla--赋值前做点处理
delattr
getattribute
getattr user
打印 user: None
四、容器相关的魔法方法
class Fibonacci ( ) :
"""
Fibonacci2 生成、存储斐波那契数列
"""
def __init__ ( self, n= 20 , a= 1 , b= 1 ) :
self. length = n
self. list = [ a, b]
self. i = 0
for each in range ( n- 2 ) :
temp = a + b
a, b = b, temp
self. list . append( temp)
self. a = a
self. b = b
def __setitem__ ( self, key, value) :
if key== 0 :
self. a = value
elif key== 1 :
self. b = value
else :
print ( "仅支持给index=0,1 赋值" )
return None
a = self. a
b = self. b
self. list = [ self. a, self. b]
for each in range ( self. length- 2 ) :
temp = a + b
a, b = b, temp
self. list . append( temp)
def __getitem__ ( self, key) :
if isinstance ( key, int ) :
return self. list [ key]
elif isinstance ( key, slice ) :
start = key. start
stop = key. stop
step = key. step
return self. list [ start: stop: step]
def __delitem__ ( self, key) :
print ( "不支持del" )
def __iter__ ( self) :
return self
def __next__ ( self) :
if 0 <= self. i < self. length:
temp = self. list [ self. i]
self. i += 1
return temp
else :
self. i = 0
raise StopIteration
def __contains__ ( self, item) :
return item in self. list
def __reversed__ ( self) :
return self. list [ : : - 1 ]
def __str__ ( self) :
string = ""
for each in self. list :
string += f", {each}"
return string[ 2 : ]
def __len__ ( self) :
return self. length
fibonacci = Fibonacci( 10 )
print ( fibonacci)
fibonacci[ 0 ] = 1
fibonacci[ 1 ] = 2
fibonacci[ 2 ] = 3
del fibonacci[ 1 ]
print ( fibonacci)
print ( "切片:" , fibonacci[ : : - 1 ] )
a = sorted ( fibonacci)
b = reversed ( fibonacci)
print ( "sorted:" , a)
print ( "reversed:" , b)
print ( 2 in fibonacci)
print ( 2 not in fibonacci)
for each in fibonacci:
print ( each)
1, 1, 2, 3, 5, 8, 13, 21, 34, 55
仅支持给index=0,1 赋值
不支持del
1, 2, 3, 5, 8, 13, 21, 34, 55, 89
切片: [89, 55, 34, 21, 13, 8, 5, 3, 2, 1]
sorted: [1, 2, 3, 5, 8, 13, 21, 34, 55, 89]
reversed: [89, 55, 34, 21, 13, 8, 5, 3, 2, 1]
True
False
1
2
3
5
8
13
21
34
55
89
五、 算数操作相关的魔法方法
class Matrix ( ) :
"""矩阵简单运算"""
def __init__ ( self, value) :
self. value = value
self. shape = ( len ( value) , len ( value[ 0 ] ) )
for each in value:
if len ( each) != len ( value[ 0 ] ) :
raise TypeError( "类型错误" )
def __add__ ( self, other) :
if other. shape != self. shape:
raise TypeError( "不同shape矩阵不能相加" )
result = [ ]
for i in range ( self. shape[ 0 ] ) :
temp = [ ]
if self. shape[ 0 ] > 0 :
for j in range ( self. shape[ 1 ] ) :
temp. append( self. value[ i] [ j] + other. value[ i] [ j] )
else :
temp = self. value[ i] + other. value[ i]
result. append( temp)
return Matrix( result)
def __sub__ ( self, other) :
if other. shape != self. shape:
raise TypeError( "不同shape矩阵不能相加" )
result = [ ]
for i in range ( self. shape[ 0 ] ) :
temp = [ ]
if self. shape[ 1 ] > 0 :
for j in range ( self. shape[ 1 ] ) :
temp. append( self. value[ i] [ j] - other. value[ i] [ j] )
else :
temp = self. value[ i] - other. value[ i]
result. append( temp)
return Matrix( result)
def __mul__ ( self, other) :
print ( other)
if other. shape != self. shape:
raise TypeError( "不同shape矩阵不能相加" )
result = [ ]
add = 0
for i in range ( self. shape[ 0 ] ) :
temp = [ ]
if self. shape[ 1 ] > 0 :
for j in range ( self. shape[ 1 ] ) :
add2 = 0
for k in range ( self. shape[ 1 ] ) :
add2 += ( self. value[ i] [ k] * other. value[ k] [ j] )
temp. append( add2)
result. append( temp)
else :
add += self. value[ i] * other. value[ i]
result = add if self. shape[ 1 ] <= 0 else result
return Matrix( result)
def __str__ ( self) :
string = ""
for each in self. value:
string += f"{each}\n"
return string
a = Matrix( [ [ 1 , 2 ] , [ 3 , 4 ] ] )
b = Matrix( [ [ 1 , 1 ] , [ 1 , 1 ] ] )
c = a + b
print ( a, b)
print ( c, type ( c) )
print ( a - b)
print ( a * b)
[1, 2]
[3, 4]
[1, 1]
[1, 1]
[2, 3]
[4, 5]
<class '__main__.Matrix'>
[0, 1]
[2, 3]
[1, 1]
[1, 1]
[3, 3]
[7, 7]