# __名字__
# 类中的特殊方法\内置方法
# 双下方法
# 魔术方法 magic_method
# 类中的每一个双下方法都有它自己的特殊意义
# __call__ 相当于 对象()
class A:
def __call__(self, *args, **kwargs):
print('执行了CALL方法')
class B(A):
def __init__(self,cls):
self.a = cls()
self.a()
a = A()
a() #对象() ==相当于调用__call__方法
A()() #类名()(),相当于先实例化得到一个对象,再对对象(),==>和上面的结果一样,相当于调用__call__方法
B(A)
# __len__ len(obj)
# 内置函数和类的内置方法是由奸情的
class A:
def __init__(self,a):
self.a = a
def __len__(self):
return len(self.a)
a = A([1,23,4,5])
b = A([(1,2),(3,4),(5,6)])
c = A({'a':(1,2),'b':(3,4),'c':(5,6)})
d = A('1,23,45')
print(len(a)) #len(a)相当于调用了这个a的__len__方法
print(len(b)) #__len__方法return的值就是len函数的返回值
print(len(c)) #如果一个对象没有__len__方法,那么这个len函数就会报错
print(len(d))
# __new__ 特别重要 开辟内存空间的 类的构造方法
# __new__ # ==> 构造方法
# __init__ # ==> 初始化方法
class Single:
def __new__(cls, *args, **kwargs):
# print('在new方法里')
obj = object.__new__(cls) # 1.开辟一个空间,属于对象的
print('在new方法里',obj) #在new方法里 <__main__.Single object at 0x000001B0B5B82F08>
return obj # 2.把对象的空间传给self,执行init
def __init__(self):
print('在init方法里',self) #在init方法里 <__main__.Single object at 0x000001B0B5B82F08>
obj = Single() # 3.将这个对象的空间返回给调用者
#执行结果:
在new方法里 <__main__.Single object at 0x000001B0B5B82F08>
在init方法里 <__main__.Single object at 0x000001B0B5B82F08>
# 1.开辟一个空间,属于对象的
# 2.把对象的空间传给self,执行init
# 3.将这个对象的空间返回给调用者
# obj = Single()
# single的new,single没有,只能调用object的new方法
# new方法在什么时候执行???
# 在实例化之后,__init__之前先执行new来创建一块空间
# 单例类
# 如果一个类 从头到尾只能有一个实例,说明从头到尾之开辟了一块儿属于对象的空间,那么这个类就是一个单例类
# class A:pass
# a = A()
# a2 = A()
# a3 = A()
# print(a,a2,a3)
# 单例类
class Single:
__ISINCTANCE = None
def __new__(cls, *args, **kwargs):
if not cls.__ISINCTANCE:
cls.__ISINCTANCE = object.__new__(cls)
return cls.__ISINCTANCE
def __init__(self,name,age):
self.name = name
self.age = age
print(self) #<__main__.Single object at 0x00000209021C60C8>
#<__main__.Single object at 0x00000209021C60C8>
obj1 = Single('alxe',12)
obj2 = Single('ctl',112)
print(obj1.name,obj1.age)
print(obj2.name,obj2.age)
print(obj1)
print(obj2)
#执行过程:
ctl 112
ctl 112
<__main__.Single object at 0x000002E7F6DB7148>
<__main__.Single object at 0x000002E7F6DB7148>
# __str__
class Student:
def __str__(self):
return '%s %s %s'%(self.school,self.cls,self.name)
def __init__(self,name,stu_cls):
self.school = 'oldboy'
self.name = name
self.cls = stu_cls
he = Student('黄河','py14')
print(he)
hang = Student('杭州','py14')
print(hang) # print一个对象相当于调用一个对象的__str__方法
print(str(he)) # 内置的数据类型,内置的类,相当于执行__str__
print('学生1 : %s'%he) # '%s'%obj,相当于执行obj.__str__方法
#执行结果:
oldboy py14 黄河
oldboy py14 杭州
oldboy py14 黄河
学生1 : oldboy py14 黄河
# print一个对象相当于调用一个对象的__str__方法
# str(obj),相当于执行obj.__str__方法
# '%s'%obj,相当于执行obj.__str__方法
待整理:
# x = 5
# y = 6
# print(x.__add__(y))
# print(x+y) # 语法糖
# class MyType:
# def __init__(self,s):
# self.s = s
#
# def __add__(self, other): # __sub__ __mul__ __div__
# return self.s.count('*') + other.s.count('*')
#
# obj1 = MyType('asjkfhk***17264****')
# obj2 = MyType('asjkfhk***17***')
# print(obj1 + obj2)
# print(obj1.__add__(obj2))
# print('ashglhg**uowqeyo88'.count('*'))
# __str__ : str(obj),要求必须实现了__str__,要求这个方法的返回值必须是字符串str类型
# print %s str
# __repr__: 是__str__的备胎.如果有__str__方法,那么# print %s str都先去执行__str__方法,并且使用__str__的返回值
# 如果没有__str__,那么 print %s str都会执行repr
# repr(obj),%r
# 在子类中使用__str__,先找子类的__str__,没有的话要向上找,只要父类不是object,就执行父类的__str__
# 但是如果出了object之外的父类都没有__str__方法,就执行子类的__repr__方法,如果子类也没有,
# 还要向上继续找父类中的__repr__方法.
# 一直找不到 再执行object类中的__str__方法
# a = '123'
# print(a)
# print(repr(a))
# class A:
# def __init__(self,name):
# self.name = name
# def __str__(self):
# return '**%s**'%self.name
# def __repr__(self):
# return self.name
#
# class B(A):
# def __init__(self,name):
# self.name = name
# def __repr__(self):
# return '***'
#
# a = B('alex')
# print(a)
# print(str(a),repr(a))
# print('%s | %r'%(a,a))
# print('---%r---'%('abc'))
# print('---%s---'%('abc'))
# __str__ __repr__ : repr