python类继承和封装
Python面向对象程序设计类的封装与继承用法示例本文实例讲述了python面向对象程序设计类的封装与继承用法。分享给大家供大家参考,具体如下:
访问限制(封装)
1、概念
面向对象语言的三大特征:封装, 继承, 多态。
广义的封装: 类和函数的定义本身就是封装的体现。
狭义的封装:一个类的某些属性,不希望外界直接访问,而是把这个属性私有化[只有当前类持有],然后暴露给外界一个访问的方法。
封装的本质:就是属性私有化的过程。
封装的好处:提供了数据的复用性,保证了数据的安全性。
举例:插排
2、使用
|
class person( object ): def __init__( self , name, age, height, weight, money): self .name = name self .__age__ = age self .weight = weight self .__money = money self .__height = height def run( self ): print ( self .__money) def eat( self ): print ( "eat" ) # 通过内部方法,去修改、获取私有属性 # 通过自定义的方法实现对私有属性的赋值与取值 # set方法:setxxx def setmoney( self , money): # 数据的过滤 if money < 0 : money = 0 self .__money = money # get方法:getxxx def getmoney( self ): return self .__money per = person( "hanmeimei" , 20 , 170 , 55 , 10000 ) # 1.属性被私有化之后的访问 # 如果要让内部属性不被外部直接访问,在属性前加两个下划线(__), # 在python中如果在属性前面加两个下划线,name这个属性就变成了私有属性[private] # 私有属性的含义:在外界不能像以前那么直接访问 # print(per.__money) #无法在外界直接访问 per.run() # 内部可以访问 # 2.解决办法: 如何对私有属性取值和赋值 # 属性被私有化之后,可以通过get/set的方法进行访问 per.setmoney( 10 ) print (per.getmoney()) # 3.工作原理 # 不能直接访问per.__money是因为python解释器把__money变成了_person__money # 仍然可以使用_person__money去访问,但是强烈不建议这么干,不同的解释器可能存在解释的变量名不一致的问题 per._person__money = 1 print (per.getmoney()) # 4.特殊情况 # 在python中 __xxx__ 属于特殊变量,将不再属于私有变量,可以直接访问 print (per.__age__) # 在python中 __xxx变量,这样的实例变量外部是可以访问的,但是,按照约定的规则 # 当我们看到这样的变量时,意思虽然是"虽然我可以被访问,但是请把我视为私有变量,不要直接访问我" print (per._person__height) |
输出:
10000
10
1
20
170
继承
1、概念
如果两个或者两个以上的类具有相同的属性和方法,我们可以抽取一个类出来,
在抽取的类中声明公共的部分
被抽取出来的类 ——父类 超类 基类
其他类 —— 子类 派生类
他们之间的关系 ——子类继承自父类
2、单继承
简单来说,一个子类只有一个父类,被称为单继承
演示:test.py 文件
注意:在使用继承时,尽量一个类存在于一个模块中
|
from person import person from student import student from worker import worker per = person( "aa" , 1 , 2 ) stu = student( "tom" , 18 , 12345 , 110 ) print (stu.name, stu.age) stu.run() print (stu.stuid) #私有属性 #print(stu.__money) print (stu.getmoney()) #通过继承过来的共有方法访问私有属性 #stu.stufunc() wor = worker( "lilei" , 20 , 111 ) print (wor.name, wor.age) wor.eat( "apple" ) #子类对象调用父类同名的函数,则优先调用子类中的函数 #本质是子类中的方法覆盖了父类中同名的函数 wor.run() print (per.getmoney()) #父类对象不能访问子类特有的属性或方法 #print(per.stuid) |
输出:
tom 18
run
110
12345
lilei 20
eat apple
子类中的run方法被调用了
2
person.py文件:
|
#以前的写法 class person(object): #但是实质上,如果没有显示的写出父类,则这个类的父类默认为object #object是所有类的父类或者超类 class person( object ): #构造方法 def __init__( self , name, age, money): self .name = name self .age = age self .__money = money #get/set方法 def setmoney( self , money): self .__money = money def getmoney( self ): return self .__money def run( self ): print ( "run" ) def eat( self , food): print ( "eat" , food) |
|
#student.py文件 from person import person class student(person): def __init__( self , name, age, money, stuid): #调用父类中的构造方法 #方法1 super(当前类,self).__init__(参数列表) #super(student,self).__init__(name, age, money, stuid) #方法2 父类名.__init__(属性列表) person.__init__( self , name, age, money) #子类可以有一些自己独有的属性 self .stuid = stuid def setfunc( self ): print ( self .__money) |
|
#worker.py文件 from person import person class worker(person): def __init__( self , name, age, money): super (worker, self ).__init__(name, age, money) # 在子类中定义和一个父类中重名的函数 def run( self ): print ( "子类中的run方法被调用了" ) |
总结:
继承的特点:
a. 子类对象可以直接访问父类中未私有的对象
b. 子类对象可以调用父类中的方法
c. 父类对象不能访问子类中特有的属性或者方法
优缺点:
优点:
1.可以简化代码,减少冗余
2.提高代码的维护性
3.提高了代码的安全性
缺点:
耦合和内聚被用来描述类与类之间的关系,耦合性越低,内聚性越高,说明代码越好。
但是,在继承关系中,耦合性相对比较高,如果修改父类,子类也会随着变化。
3、多继承
顾名思义:就是一个子类中可以有多个父类,比如一个孩子有一个爸爸一个妈妈
|
from child import child def main(): c = child( 300 , 100 , "xiaoming" ) print (c.money, c.facevalue) c.play() c.eat() #注意:如果多个父类中的方法名相同,默认调用的是子类括号中排前面的父类中的方法 #此时调用的是father中func方法 if __name__ = = "__main__" : main() |
输出:
300 100
play
eat
|
#father.py文件 class father( object ): def __init__( self , money): self .money = money def play( self ): print ( "play" ) def func( self ): print ( "father" ) |
|
#mother.py文件 class mother( object ): def __init__( self , facevalue): self .facevalue = facevalue def eat( self ): print ( "eat" ) def func( self ): print ( "mother" ) |
|
#child.py文件 from father import father from mother import mother class child(father, mother): def __init__( self , money, facevalue,name): #注意:分别调用各个父类中的构造方法 father.__init__( self , money) mother.__init__( self , facevalue) #子类中同样可以有自己独有的特性 self .name = name |
总结:
子类可以从多个父类中继承属性和方法
一个父类可以有多个子类
一个子类可以有多个父类
4、函数重写
4.1、系统函数
|
''' 重写:将函数重写一遍 __str__():在调用print打印对象时自动调用,是给用户用的,是一个描述对象的方法. __repr__():是给机器用的,在python解释器里面直接敲对象名在回车后调用方法 注意:在没有str,且有repr时,str=repr ''' class animal( object ): def __init__( self , name, age, height, weight): self .name = name self .age = age self .height = height self .weight = weight def __str__( self ): return "%s-%d-%d-%d" % ( self .name, self .age, self .height, self .weight) ani = animal( "大黄" , 5 , 60 , 25 ) #print(per.name, per.age, per.height, per.weight) #在打印ani时自动调用str函数 print (ani) #优点或者使用时机:当一个对象的属性值很多,并且都需要打印,重写__str__方法后,简化了代码,方便查看. |
输出:
大黄-5-60-25
5、自定义函数
重写函数的时机:当父类中函数的功能满足不了子类的需求时,就可以进行重写。
演示:
|
from smallanimal import smallanimal from cat import cat c = cat() c.func() |
|
#smallanimal.py文件 class smallanimal( object ): def func( self ): print ( "wwww" ) |
|
#cat.py文件 from smallaniml import smallanimal class cat(smallanimal): def func( self ): print ( "呵呵呵" ) |
希望本文所述对大家python程序设计有所帮助。
原文链接:https://blog.csdn.net/lm_is_dc/article/details/80167458