一:self 指针
self 形式参数, python 内部传递. self 指代对象的内存地址
1 classoldboy:2 deffetch(self):3 print(self)4
5 obj1 =oldboy()6 print(obj1,obj1.fetch())7
8 obj2 =oldboy()9 print(obj2,obj2.fetch())10
11
12 C:\Python35\python.exe D:/python/day8/pr.py13 <__main__.oldboy object at>
14 <__main__.oldboy object at>None15 <__main__.oldboy object at>
16 <__main__.oldboy object at> None
二、 封装
将内容封装到某处,以后再去调用内封装在某处的内容。对向对象封装来说,其实就是将构造方法将内容封装到对象。然后通过self 间接或者通过对象获取被封装的内容
所以在使用面向对象的封装特性的时候,需要:
将内容封装在某处
从某处调用被封装的内容
第一步: 将内容封装到某处
1 classFoo:2
3 #构造方法,根据类创建对象时候自动执行
4 def __init__(self,name, age):5 self.name =name6 self.age =age7
8 #执行init方法, 将yy 和18 封装到 obj1(self) 的 name 和age
9 obj1 = Foo('yy',18)10
11 #执行init方法, 将xx 和18 封装到 obj2(self) 的 name 和age
12 obj2 = Foo('xx',18)13
14 #self 是形式参数,当执行obj1 = Foo()的时候,self 相当于obj1
15 #所以其实内容就被封装到了 obj1 。 每个对象都有name 和 age
第二步:从某处调用
调用被封装的内容时,有2个情况
通过对象直接调用
通过self间接调用
1:通过对象直接调用
1 print(obj1.name)2 print(obj2.name)
2:通过self间接调用
执行类中的方法,通过self 间接将调用的封装的内容
1 classFoo:2
3 #构造方法,根据类创建对象时候自动执行
4 def __init__(self,name, age):5 self.name =name6 self.age =age7
8 defdetail(self):9 print(self.name)10 print(self.age)11
12 #执行init方法, 将yy 和18 封装到 obj1(self) 的 name 和age
13 obj1 = Foo('yy',18)14
15 #执行init方法, 将xx 和18 封装到 obj2(self) 的 name 和age
16 obj2 = Foo('xx',18)17
18 obj1.detail()19
20 obj2.detail()
三、继承
继承、面向对象中的继承和显示生活中的继承相同,子可以继承父的内容
对于面向对象继承来说,其实就是将多个类共有的方法提取到父类中。子类仅需继承父类而 不必一一实现
除了父类和子类的称谓,也可以称谓 派生类 和 基类
1 单继承
如果子类和父类有相关的方法。优先子类方法
1 classAnimal:2
3 defeat(self):4 print('%s 吃'%self.name)5
6
7 classcat(Animal):8 def __init__(self,name):9 self.name =name10
11 classdog(Animal):12 def __init__(self,name):13 self.name =name14
15
16 cats = cat('猫')17 cats.eat()18
19 dogs = dog('够')20 dogs.eat()
2、多继承
1: 2个父系没有共同节点 深度优先 子类 -- > 左父类 -- 左爷爷 -- >右父类 -- > 右爷爷
2: 2个父系有共同节点 广度优先 子类 -- > 左父 -->右父 -- > 爷爷
3: 在执行中,针对每一个调用的函数,都从子类开始查找。 例如在子类在爷爷f1(),又调用了 f2(), 本质为self.f2(),self 为子类 对象。因此将从子类开始重新查找f2()
前面2个情况
三、多态
Python不支持多态,也不用到多态,多态的概念应用JAVA
其他语言需要指定对象的类型。
1 classF1:2 pass
3
4
5 classS1(F1):6 defshow(self):7 print
8 'S1.show'
9
10
11 classS2(F1):12 defshow(self):13 print
14 'S2.show'
15
16
17 #由于在Java或C#中定义函数参数时,必须指定参数的类型
18 #为了让Func函数既可以执行S1对象的show方法,又可以执行S2对象的show方法,所以,定义了一个S1和S2类的父类
19 #而实际传入的参数是:S1对象和S2对象
20
21 defFunc(F1 obj):22 """Func函数需要接收一个F1类型或者F1子类的类型"""
23
24 print
25 obj.show()26
27 s1_obj =S1()28 Func(s1_obj) #在Func函数中传入S1类的对象 s1_obj,执行 S1 的show方法,结果:S1.show
29
30 s2_obj =S2()31 Func(s2_obj) #在Func函数中传入Ss类的对象 ss_obj,执行 Ss 的show方法,结果:S2.show
32
33 Python伪代码实现Java或C #的多态
Python 不需要制定类型
1 classF1:2 pass
3
4
5 classS1(F1):6
7 defshow(self):8 print 'S1.show'
9
10
11 classS2(F1):12
13 defshow(self):14 print 'S2.show'
15
16 defFunc(obj):17 printobj.show()18
19 s1_obj =S1()20 Func(s1_obj)21
22 s2_obj =S2()23 Func(s2_obj)24
25 Python “鸭子类型”
四、基类构造方法
1:类名称后加()自动执行__init__
2: 使用super 可以执行父类构造方法
3:可以通过A.__init__ 直接执行父类的构造方法。
classA:def __init__(self):print('A构造方法')
self.ty= 'A'
classB(A):def __init__(self):print('B构造方法')
self.n= 'B'
#super执行父类构造方法
super(B,self).__init__()#也可以直接执行
A.__init__(self)#类名称后面加()自动执行
b = B()
总结:
面向对象是一种变成方式,此编程方式实现基于对类和对象的使用
类是一个模板,模板中包装了多个函数,共同使用
对象,根据模板创建的实例,实例用于调用被封装在类中的函数
面向对象的三个特性:封装、继承、多态
类以及类的方法在内存中仅有一份,根据类创建的每一个对象在内存中需要存一份
在创建对象时,对象中除了封装name,age 等属性外,还会保存一个对象指针,指向当前对象的类
通过对象.xxxx 执行的时候:
1:根据当前对象中的类对象指针找到类中的方法
2:将对象obj1 当做参数传递给方法的第一个参数self
扩展:
重载:函数名相同,参数个数不同(Python不支持)
重写:派生类中实现了基类的方法