python面向对象三大特征,面向对象
分类:计算机编程

面向对象-组合

风流罗曼蒂克、面向进度与面向对象的简要介绍

一、继承

大器晚成 什么是多态动态绑定(在这里起彼伏的背景下行使时,一时也称得上多态性)

1.如何是构成

1.面向过程:

  定义:面向进程的主次设计的主干是经过(流水生产线式思维),进度即消除难题的步调,面向进程的准备就好比精心设计好一条流水生产线,考虑周详几时管理什么东西。

  优点:非常大的回降了写程序的复杂度,只要求顺着要实践的步骤,积聚代码就能够。

  瑕疵:大器晚成套流水线恐怕流程正是用来废除二个标题,代码一着不慎满盘皆输。

1.怎么世袭

接二连三是大器晚成种创造新类的不二等秘书技,新建的类能够世袭叁个或八个父类(python扶持多接二连三),父类又可称之为基类或超类,新建的类称为派生类或子类。**

多态性是指在不思虑实例类型的图景下选择实例

  组合指的是某二个目的具备贰特性能,该属性的值是别的贰个类的靶子

2.面向对象:

  定义:面向对象的程序设计的基本是指标(天神式思维),要掌握对象为什么物,必须把自身真是老天爷,苍天眼里世间存在的万物皆为目的,海市蜃楼的也可以成立出来。

  优点:解决了前后相继的增添性。对某叁个对象单独修改,会马上反映到全方位体系中,如对游乐中一位士参数的特点和手艺修正都非常轻巧。

  劣势:可控性差,不能够向面向进程的程序设计流水生产线式的能够很精准的推测难点的管理流程与结果,面向对象的前后相继黄金时代旦初阶就由对象之间的相互肃清难题,即正是上天也力不从心预测最后结出。

2.为什么要有继续

子类会“”遗传”父类的属性,进而解决代码重用难点,收缩代码的冗余

在面向对象方法中一般是这样表述多态性:
向不同的对象发送同一条消息(!!!obj.func():是调用了obj的方法func,又称为向obj发送了一条消息func),不同的对象在接
收时会产生不同的行为(即方法)。
也就是说,每个对象可以用自己的方式去响应共同的消息。所谓消息,就是调用函数,不同的行为就是指不同的实现,即执行不同的函数
。

比如:老师.下课铃响了(),学生.下课铃响了(),老师执行的是下班操作,学生执行的是放学操作,虽然二者消息一样,但是执行的效
果不同
 1 class Foo:
 2     xxx = 111
 3 
 4 class Bar:
 5     yyy = 222
 6 
 7 obj = Foo()
 8 obj.attr = Bar()
 9 
10 print(obj.xxx)
11 >>>111
12 print(obj.attr.yyy)
13 >>>222

二、面向对象的家庭成员介绍

3.怎么使用持续

eg:

class ParentClass1: # 定义父类1
    pass

class ParentClass2: # 定义父类2
    pass

class Subclass1(ParentClass1): # 单继承 父类1
    pass

class Subclass2(ParentClass1,ParentClass2):  # 多继承多个父类  父类1 父类2
    pass

print(Subclass1.__bases__)  # 查看所有父类信息
print(Subclass2.__bases__)  # 查看所有父类信息

结果:以元组的形式返回
(<class '__main__.ParentClass1'>,)
(<class '__main__.ParentClass1'>, <class '__main__.ParentClass2'>)

 

多态性

 

1.初识类和指标

对象:

(1)指任何物体(‘万事万物皆为目的’)

(2)不一致的靶子有分裂的性情,万物都有浮动——对象的措施。

(3)对于别的三个属性都享有3个方面:属性所属的对象,属性的值,属性的称呼。对象某些属性并非风度翩翩层不改变的。

类:

(1)人以群分——类定义对象——饼干模具临蓐饼干

(2)类是由相通的表征结合,类是概念同风流罗曼蒂克类具备目标的变量和办法的蓝图。

(3)对象的共性抽象为类,类的实例化正是目的。

4.继续与虚空(先抽象再持续)

先抽象:收取对象之间相同之处获得了类,在计算类与类之间的相近获得父类

再持续:(子类世袭父类,子类可以遗传父类属性卡塔尔国是遵照抽象的结果,通过编制程序语言去落实它,肯定是先资历抽象这么些历程,技巧通过一连的艺术去发挥出抽象的构造。

peo=People()
dog=Dog()
pig=Pig()

#peo、dog、pig都是动物,只要是动物肯定有talk方法
#于是我们可以不用考虑它们三者的具体是什么类型,而直接使用
peo.talk()
dog.talk()
pig.talk()

#更进一步,我们可以定义一个统一的接口来使用
def func(obj):
    obj.talk()

2.为啥要用组合

1.类的扬言:

def functionName(args):
     '函数文档字符串'
      函数体 

'''
class 类名:
    '类的文档字符串'
    类体
'''

#我们创建一个类
class Data:
    pass

class Person:   #定义一个人类
    role = 'person'  #人的角色属性都是人
    def walk(self):  #人都可以走路,也就是有一个走路方法,也叫动态属性
        print("person is walking...")

5.派生与重用

派生:子类定义本人新的性质,假诺与父类同名,以子类本身的为准

图片 1图片 2

# 父类
class People:
    def __init__(self, name, age, sex):
        self.name = name
        self.age = age
        self.sex = sex

    def func1(self):
        print('People.func1')


# 子类 派生自己的属性
class Teacher(People):
    def __init__(self, name, age, sex, level, salary):
        self.name = name
        self.age = age
        self.sex = sex

        self.level = level
        self.salary = salary

    def func1(self):
        print('Teacher.func1')


# 实例化
tea1 = Teacher('fixd', 18, 'male', 9, 3.1)
print(tea1.name, tea1.age, tea1.sex, tea1.level, tea1.salary)

# 结果
fixd 18 male 9 3.1

亲自去做代码

采纳:在子类派生出的新点子中选用父类的效应

办法风华正茂:毫不遮盖地调用(其实与后续未有啥样关联的)

# 父类
class People:
    def __init__(self, name, age, sex):
        self.name = name
        self.age = age
        self.sex = sex


# 子类 "指名道姓" 调用父类的属性
class Teacher(People):
    def __init__(self, name, age, sex, level, salary):
        People.__init__(self, name, age, sex)
        self.level = level
        self.salary = salary

格局二、super(卡塔尔(英语:State of Qatar)调用(严刻重视于继续)

*  ps:super(卡塔尔(قطر‎的重返值是一个至极的指标,该对象非常用来调用父类中的属性*

*  驾驭:在python第22中学,需求super(自身的类名,self卡塔尔国*

# 父类
class People:
    def __init__(self, name, age, sex):
        self.name = name
        self.age = age
        self.sex = sex


# 子类 super() 调用父类的属性
class Teacher(People):
    def __init__(self, name, age, sex, level, salary):       
        super().__init__(name, age, sex)
        self.level = level
        self.salary = salary 

专心:以上三种艺术都能够动用,在实际的编码职业中,推荐应用统意气风发的后生可畏种方法

 

图片 3图片 4

#super()会严格按照mro列表从当前查找到的位置继续往后查找
class A:
    def test(self):
        print('A.test')
        super().f1()
class B:
    def f1(self):
        print('from B')
class C(A,B):
    pass

c=C()
print(C.mro()) #C->A->B->object


c.test()

mro列表

 

赤麻鸭类型

  通过为某四个对象增添属性(属性的值是其余两个类的对象卡塔尔(英语:State of Qatar)的措施,能够直接地将四个类关联/整合/组合到一齐

2.类有二种意义:

性情援用:

class Person:   #定义一个人类
    role = 'person'  #人的角色属性都是人
    def walk(self):  #人都可以走路,也就是有一个走路方法
        print("person is walking...")


print(Person.role)  #查看人的role属性
print(Person.walk)  #引用人的走路方法,注意,这里不是在调用

实例化:类名加括号正是实例化,会自动触发__init__函数的运作,能够用它来为每一种实例定制自身的风味

class Person:   #定义一个人类
    role = 'person'  #人的角色属性都是人
    def __init__(self,name):
        self.name = name  # 每一个角色都有自己的昵称;

    def walk(self):  #人都可以走路,也就是有一个走路方法
        print("person is walking...")


print(Person.role)  #查看人的role属性
print(Person.walk)  #引用人的走路方法,注意,这里不是在调用

实例化的进度正是类——>对象的进度

原本大家唯有一个Person类,在这里个进度中,发生了二个egg对象,有本身具体的名字、攻击力和生命值。

语法:对象名 = 类名(参数)

class Person:   #定义一个人类
    role = 'person'  #人的角色属性都是人
    def __init__(self,name):
        self.name = name  # 每一个角色都有自己的昵称;

    def walk(self):  #人都可以走路,也就是有一个走路方法
        print("person is walking...")

aray = Person('zbk')
print(aray.name)   #查看属性直接 对象名.属性名
print(aray.walk())  #调用方法,对象名.方法名()

5.属性查找

'''
1、新式类:
    继承object的类,以及该类的子类,都是新式类

    在python3中,如果一个类没有指定继承的父类,默认就继承object
    所以说python3中所有的类都是新式类

2、经典类(只有在python2才区分经典类与新式类):
    没有继承object的类,以及该类的子类,都是经典类
'''

单继承名称空间的探求顺序:

指标自己-------->>当前类-------->>父类-------->>object      # 查找不到,报错

多三番九遍名称空间的查究顺序:

图片 5

图片 6

在菱形世袭的背景下,查找属性
1、优良类:深度优先
2、新式类:广度优先

 

逗比每十六日:

  从而减少类与类之间代码冗余

关于self

self:在实例化时自动将指标/实例本身传给__init__的首先个参数,你也得以给他起各自的名字,可是正常人都不会如此做。
因为您瞎改外人就不认得

类属性的增加补充:

一:我们定义的类的属性到底存到哪里了?有两种方式查看
dir(类名):查出的是一个名字列表
类名.__dict__:查出的是一个字典,key为属性名,value为属性值

二:特殊的类属性
类名.__name__# 类的名字(字符串)
类名.__doc__# 类的文档字符串
类名.__base__# 类的第一个父类(在讲继承时会讲)
类名.__bases__# 类所有父类构成的元组(在讲继承时会讲)
类名.__dict__# 类的字典属性
类名.__module__# 类定义所在的模块
类名.__class__# 实例对应的类(仅新式类中)

面向对象小结——定义及调用的固化方式

class 类名:
    def __init__(self,参数1,参数2):
        self.对象的属性1 = 参数1
        self.对象的属性2 = 参数2

    def 方法名(self):pass

    def 方法名2(self):pass

对象名 = 类名(1,2)  #对象就是实例,代表一个具体的东西
                  #类名() : 类名 括号就是实例化一个类,相当于调用了__init__方法
                  #括号里传参数,参数不需要传self,其他与init中的形参一一对应
                  #结果返回一个对象
对象名.对象的属性1   #查看对象的属性,直接用 对象名.属性名 即可
对象名.方法名()     #调用类中的方法,直接用 对象名.方法名() 即可

二、封装

  Python崇尚硬尾鸭类型,即‘要是看起来像、叫声音图像并且走起路来像绿头鸭,那么它正是树鸭’

 1 class Foo1:
 2     pass
 3 class Foo2:
 4     pass
 5 class Foo3:
 6     pass
 7 
 8 class Bar:
 9     pass
10 
11 obj_from_bar=Bar()
12 
13 obj1=Foo1()
14 obj2=Foo2()
15 obj3=Foo3()
16 
17 obj1.attr1=obj_from_bar
18 obj2.attr2=obj_from_bar
19 obj3.attr3=obj_from_bar

三、面向对象的咬合

1.哪些是包装

字面上的意趣正是,把东西隐蔽起来了。

在python中的封装正是把 类中的属性(变量、函数)遮盖起来

python程序员经常依据这种表现来编写程序。比如,要是想编写现存对象的自定义版本,能够延续该指标

 

1.哪些是整合?

答:软件重用的基本点艺术除了三回九转之外还应该有别的豆蔻梢头种情势,即:组合

重新组合指的是,在多个类中以别的二个类的对象作为数据属性,称为类的结缘

组合表现的是:  谁有什么的关系。
例如:  人有武器 、   学校有学生  、 学生有课程

组成例子1:

class Weapon:
    def prick(self, obj):  # 这是该装备的主动技能,扎死对方
        obj.life_value -= 500  # 假设攻击力是500

class Person:  # 定义一个人类
    role = 'person'  # 人的角色属性都是人

    def __init__(self, name):
        self.name = name  # 每一个角色都有自己的昵称;
        self.weapon = Weapon()  # 给角色绑定一个武器;

egg = Person('egon')
egg.weapon.prick() 
#egg组合了一个武器的对象,可以直接egg.weapon来使用组合类中的所有方法

整合例子2:

圆环是由三个圆组成的,圆环的面积是外面圆的面积减去内部圆的面积。圆环的周长是里面圆的周长加上海外国语高校表圆的周长。
本条时候,我们就率先落实叁个圆形类,总结三个圆的周长和面积。然后在"环形类"中组成圆形的实例作为团结的习性来用

图片 7图片 8

from math import pi

class Circle:
    '''
    定义了一个圆形类;
    提供计算面积(area)和周长(perimeter)的方法
    '''
    def __init__(self,radius):
        self.radius = radius

    def area(self):
         return pi * self.radius * self.radius

    def perimeter(self):
        return 2 * pi *self.radius


circle =  Circle(10) #实例化一个圆
area1 = circle.area() #计算圆面积
per1 = circle.perimeter() #计算圆周长
print(area1,per1) #打印圆面积和周长

class Ring:
    '''
    定义了一个圆环类
    提供圆环的面积和周长的方法
    '''
    def __init__(self,radius_outside,radius_inside):
        self.outsid_circle = Circle(radius_outside)
        self.inside_circle = Circle(radius_inside)

    def area(self):
        return self.outsid_circle.area() - self.inside_circle.area()

    def perimeter(self):
        return  self.outsid_circle.perimeter()   self.inside_circle.perimeter()


ring = Ring(10,5) #实例化一个环形
print(ring.perimeter()) #计算环形的周长
print(ring.area()) #计算环形的面积

View Code

重新组合例子3:

用整合的点子创立了类与组合的类之间的关联,它是大器晚成种‘有’的关联,举例助教有华诞,助教教python课程

图片 9图片 10

class BirthDate:
    def __init__(self,year,month,day):
        self.year=year
        self.month=month
        self.day=day

class Couse:
    def __init__(self,name,price,period):
        self.name=name
        self.price=price
        self.period=period

class Teacher:
    def __init__(self,name,gender,birth,course):
        self.name=name 
        self.gender=gender
        self.birth=birth
        self.course=course
    def teach(self): 
        print('teaching')

p1=Teacher('egon','male', 
            BirthDate('1995','1','27'), 
            Couse('python','28000','4 months')
           ) 

print(p1.birth.year,p1.birth.month,p1.birth.day) 

print(p1.course.name,p1.course.price,p1.course.period)
''' 
运行结果: 
1 27 
python 28000 4 months 

View Code

当类之间有大名鼎鼎区别,而且很小的类是相当的大的类所急需的零器件时,用结合影比好

2.为啥要用封装

装进的真谛在于明确内外

对外掩没(类的外界只可以通过大家提供的接口对类内部的掩没属性就能够寻访)

对内开放(在类的内部能够一向动用隐蔽属性)

 

封装数据(变量)将数据隐蔽并不是我们的指标,能够透过接口的方法将数据揭示给类外面使用,在接口中大家得以对数码实行界定,达成对数码的垄断(monopoly卡塔尔国

图片 11图片 12

class Teacher:
    def __init__(self,name,age):
        # self.__name=name
        # self.__age=age
        self.set_info(name,age)

    def tell_info(self):
        print('姓名:%s,年龄:%s' %(self.__name,self.__age))
    def set_info(self,name,age):
        if not isinstance(name,str):
            raise TypeError('姓名必须是字符串类型')
        if not isinstance(age,int):
            raise TypeError('年龄必须是整型')
        self.__name=name
        self.__age=age


t=Teacher('egon',18)
t.tell_info()

t.set_info('egon',19)
t.tell_info()

演示代码

装进方法(函数)关键目标隔开分离复杂度,将类中八个函数组合,提供二个对外封装好的接口,供使用者调用,而调用者无需思索接口内复杂的落到实处过程,简化调用

图片 13图片 14

#取款是功能,而这个功能有很多功能组成:插卡、密码认证、输入金额、打印账单、取钱
#对使用者来说,只需要知道取款这个功能即可,其余功能我们都可以隐藏起来,很明显这么做
#隔离了复杂度,同时也提升了安全性

class ATM:
    def __card(self):
        print('插卡')
    def __auth(self):
        print('用户认证')
    def __input(self):
        print('输入取款金额')
    def __print_bill(self):
        print('打印账单')
    def __take_money(self):
        print('取款')

    def withdraw(self):
        self.__card()
        self.__auth()
        self.__input()
        self.__print_bill()
        self.__take_money()

a=ATM()
a.withdraw()

隔离复杂度的例子

以身作则代码

也得以创设贰个外观和作为像,但与它无任何关系的全新对象,后面一个日常用于保存程序组件的松耦合度。

3.怎么用结合

四、面向对象的三大特色

3.怎么用包装

在python中用双下划线初叶的不二秘诀将品质隐讳起来(设置成私有的)

#其实这仅仅这是一种变形操作且仅仅只在类定义阶段发生变形
#类中所有双下划线开头的名称如__x都会在类定义时自动变形成:_类名__x的形式:

class A:
    __N=0 #类的数据属性就应该是共享的,但是语法上是可以把类的数据属性设置成私有的如__N,会变形为_A__N
    def __init__(self):
        self.__X=10 #变形为self._A__X
    def __foo(self): #变形为_A__foo
        print('from A')
    def bar(self):
        self.__foo() #只有在类内部才可以通过__foo的形式访问到.

#A._A__N是可以访问到的,
#这种,在外部是无法通过__x这个名字访问到。

PS:

*1.这种体制也并未有当真含义上限制大家从外表间接访谈属性,知道了类名和性质名就可以拼盛名字:_类名__质量,然后就可以访问了,如a._A__N,**即这种操作并非严峻意义上的范围外界访谈,仅仅只是大器晚成种语法意义上的变形,首要用来界定外界的第一手访谈。


2.变形的长河只在类的定义时产生贰遍,在概念后的赋值操作,不会变形

图片 15

3.在后续中,父类假诺不想让子类覆盖本身的点子,能够将艺术定义为私有的

 

图片 16图片 17

#正常情况
>>> class A:
...     def fa(self):
...         print('from A')
...     def test(self):
...         self.fa()
... 
>>> class B(A):
...     def fa(self):
...         print('from B')
... 
>>> b=B()
>>> b.test()
from B


#把fa定义成私有的,即__fa
>>> class A:
...     def __fa(self): #在定义时就变形为_A__fa
...         print('from A')
...     def test(self):
...         self.__fa() #只会与自己所在的类为准,即调用_A__fa
... 
>>> class B(A):
...     def __fa(self):
...         print('from B')
... 
>>> b=B()
>>> b.test()
from A

示范代码

 

 

 

例1:利用标准库中定义的各样‘与公事相像’的靶子,就算那一个目的的干活章程像文件,但他们尚无继续内置文件对象的法子

 1 class OldboyPeople:
 2     school = 'Oldboy'
 3 
 4     def __init__(self, name, age, sex, ):
 5         self.name = name
 6         self.age = age
 7         self.sex = sex
 8 
 9 
10 class OldboyStudent(OldboyPeople):
11     def __init__(self, name, age, sex, score=0):
12         OldboyPeople.__init__(self, name, age, sex)
13         self.score = score
14         self.courses = []
15 
16     def choose_course(self):
17         print('%s choosing course' % self.name)
18 
19     def tell_all_course(self):
20         print(('学生[%s]选修的课程如下' % self.name).center(50, '='))
21         for obj in self.courses:
22             obj.tell_info()
23         print('=' * 60)
24 
25 
26 class OldboyTeacher(OldboyPeople):
27     def __init__(self, name, age, sex, level):
28         OldboyPeople.__init__(self, name, age, sex)
29         self.level = level
30         self.courses = []
31 
32     def score(self, stu, num):
33         stu.score = num
34 
35     def tell_all_course(self):
36         print(('老师[%s]教授的课程如下' % self.name).center(50, '*'))
37         for obj in self.courses:
38             obj.tell_info()
39         print('*' * 70)
40 
41 
42 class Course:
43     def __init__(self, c_name, c_price, c_period):
44         self.c_name = c_name
45         self.c_price = c_price
46         self.c_period = c_period
47 
48     def tell_info(self):
49         print('<课程名:%s 价钱:%s 周期:%s>' % (self.c_name, self.c_price, self.c_period))
50 
51 
52 # 创建课程对象
53 python = Course('python全栈开发', 1900, '5mons')
54 linux = Course('linux架构师', 900, '3mons')
55 
56 stu1 = OldboyStudent('刘二蛋', 38, 'male')
57 stu1.courses.append(python)
58 stu1.courses.append(linux)
59 stu1.tell_all_course()
60 
61 tea1 = OldboyTeacher('egon', 18, 'male', 10)
62 tea1.courses.append(python)
63 tea1.tell_all_course()

1.继承:

继续是生机勃勃种制造新类的诀窍,在python中,新建的类可以持续二个或多少个父类,父类又可称之为基类或超类,新建的类称为派生类或子类

4.特性(property)

哪些是特点

property是风度翩翩种极其的习性,访谈它时会施行一段功效(函数)然后重返值

eg:

图片 18图片 19

BMI指数(bmi是计算而来的,但很明显它听起来像是一个属性而非方法,如果我们将其做成一个属性,更便于理解)

成人的BMI数值:
过轻:低于18.5
正常:18.5-23.9
过重:24-27
肥胖:28-32
非常肥胖, 高于32
  体质指数(BMI)=体重(kg)÷身高^2(m)
  EX:70kg÷(1.75×1.75)=22.86

成效描述

图片 20图片 21

class People:
    def __init__(self,name,weight,height):
        self.name=name
        self.weight=weight
        self.height=height

    @property
    def bmi(self):
        return self.weight / (self.height * self.height)

# egon=People('egon',75,1.80)
#
# egon.bmi=egon.weight / (egon.height * egon.height)
# print(egon.bmi)
#
# yl=People('yangli',85,1.74)
# yl.bmi=yl.weight / (yl.height * yl.height)
# print(yl.bmi)


# 首先需要明确。bmi是算出来的,不是一个固定死的值,也就说我们必须编写一个功能,每次调用该功能
#都会立即计算一个值
egon=People('egon',75,1.80)
yl=People('yangli',85,1.74)

# 但很明显人的bmi值听起来更像一个名词而非动词
# print(egon.bmi())
# print(yl.bmi())


# 于是我们需要为bmi这个函数添加装饰器,将其伪装成一个数据属性
# egon.weight=70
# print(egon.bmi) #21.604938271604937,调用egon.bmi本质就是触发函数bmi的执行,从而拿到其返回值
# print(yl.bmi)

示范代码

 

为什么要用性子

将多个类的函数定义成特征以往,对象再去采用的时候obj.name,根本无法察觉自个儿的name是实施了一个函数然后计算出来的,这种性子的行使方法信守了合併采访的口径

PS:

【public】
这种其实就是不封装,是对外公开的
【protected】
这种封装方式对外不公开,但对朋友(friend)或者子类(形象的说法是“儿子”,
但我不知道为什么大家 不说“女儿”,就像“parent”本来是“父母”的意思,但中文都是叫“父类”)公开
【private】
这种封装对谁都不公开

python并不曾经在语法上把它们多个内建到协调的class机制中,能够通过property方法达成

图片 22图片 23

class Foo:
    def __init__(self,val):
        self.__NAME=val #将所有的数据属性都隐藏起来

    @property
    def name(self):
        return self.__NAME #obj.name访问的是self.__NAME(这也是真实值的存放位置)

    @name.setter
    def name(self,value):
        if not isinstance(value,str):  #在设定值之前进行类型检查
            raise TypeError('%s must be str' %value)
        self.__NAME=value #通过类型检查后,将值value存放到真实的位置self.__NAME

    @name.deleter
    def name(self):
        raise TypeError('Can not delete')

f=Foo('egon')
print(f.name)
# f.name=10 #抛出异常'TypeError: 10 must be str'
del f.name #抛出异常'TypeError: Can not delete'

演示代码

 

例2:体系类型有四种形态:字符串,列表,元组,但她俩直白未有一向的继续关系

 

在持续中, 若是子类有的艺术就实行子类的 若是子类未有的点子就进行父类的。 语法: class 类名(父类名): 如若不钦赐世襲的父类,暗许继承 object 子类能够动用父类的全体属性和章程。 固然子类有行家级的措施就实行自个儿的。 没救就实行父类, 子类,父类都未有,就报错。 子类中调用父类: 在类内—— super (子类名,self卡塔尔(英语:State of Qatar).方法名() 在类外—— super (子类名,对象名卡塔尔。方法名()

图片 24

python中类的三番两次分为:单世袭和多世襲

图片 25图片 26

class ParentClass1: #定义父类
    pass

class ParentClass2: #定义父类
    pass

class SubClass1(ParentClass1): #单继承,基类是ParentClass1,派生类是SubClass
    pass

class SubClass2(ParentClass1,ParentClass2): #python支持多继承,用逗号分隔开多个继承的类
    pass

View Code

提醒:若无一些名基类,python的类会默许世襲object类,object是有着python类的基类,它提供了风流倜傥部分广大格局(如__str__)的实现。

三、多态

#二者都像鸭子,二者看起来都像文件,因而就可以当文件一样去用
class TxtFile:
    def read(self):
        pass

    def write(self):
        pass

class DiskFile:
    def read(self):
        pass
    def write(self):
        pass

面向对象-多态与多态性

大浪涛沙: 大规模到校范围 抽象: 范围进一层大,共性更小 派生:父类的基础上发出子类——派生类 派生方法: 父类里未有的,可是i子类里部分 派生属性: 方法的重写: 父类里部分艺术,在子类里再度达成。

1、什么是多态

* 多态指的是均等种东西三种模样*

封装

【封装】

         隐敝对象的品质和促成细节,仅对外提供公共访谈情势。

【好处】 

  1. 将转移隔断; 

  2. 方便人民群众使用;

  3. 坚实复用性; 

  4. 拉长安全性;

【封装原则】

      1. 将无需对外提供的剧情都躲避起来;

      2. 把品质都藏匿,提供公共措施对其访谈。

1.怎样是多态

2.多态:

多态指的是风流罗曼蒂克类东西有种种样子

动物有各类形象:人,狗,猪

import abc
class Animal(metaclass=abc.ABCMeta): #同一类事物:动物
    @abc.abstractmethod
    def talk(self):
        pass

class People(Animal): #动物的形态之一:人
    def talk(self):
        print('say hello')

class Dog(Animal): #动物的形态之二:狗
    def talk(self):
        print('say wangwang')

class Pig(Animal): #动物的形态之三:猪
    def talk(self):
        print('say aoao')

 文件有各样形状:文本文件,可实践文件。如下:

import abc
class File(metaclass=abc.ABCMeta): #同一类事物:文件
    @abc.abstractmethod
    def click(self):
        pass

class Text(File): #文件的形态之一:文本文件
    def click(self):
        print('open file')

class ExeFile(File): #文件的形态之二:可执行文件
    def click(self):
        print('execute file')

意气风发 什么是多态动态绑定(在继续的背景下选择时,不时也称之为多态性)

多态性是指在不思量实例类型的意况下采纳实例:

比如:老师.下课铃响了(),学生.下课铃响了(),老师执行的是下班操作,学生执行的是放学操作,虽然二者消息一样,但是执行的效果不同

多态性分为静态多态性和动态多态性:

*  静态多态性:如别的项目都能够用运算符 进行演算*

*  动态多态性:如下*

peo=People()
dog=Dog()
pig=Pig()

#peo、dog、pig都是动物,只要是动物肯定有talk方法
#于是我们可以不用考虑它们三者的具体是什么类型,而直接使用
peo.talk()
dog.talk()
pig.talk()

#更进一步,我们可以定义一个统一的接口来使用
def func(obj):
    obj.talk()

  

硬尾鸭类型

逗比时刻:

  Python崇尚绿头鸭类型,即‘借使看起来像、叫声音图像并且走起路来像绒鸭,那么它便是潜水鸭’

python程序员日常依据这种表现来编写程序。比方,如若想编写现存对象的自定义版本,能够世襲该目的

也足以创制一个外观和作为像,但与它无别的涉及的全新对象,前者经常用于保存程序组件的松耦合度。

例1:利用规范库中定义的各个‘与公事相似’的对象,纵然那几个指标的做事方法像文件,但他俩不曾持续内置文件对象的主意

例2:连串类型有两种形状:字符串,列表,元组,但她俩直白未有直接的存在延续关系

#二者都像鸭子,二者看起来都像文件,因而就可以当文件一样去用
class TxtFile:
    def read(self):
        pass

    def write(self):
        pass

class DiskFile:
    def read(self):
        pass
    def write(self):
        pass

2、为啥要用多态   

用基类创设意气风发套统风流倜傥的规行矩步,免强子类去遵照(使用抽象类完毕),那样便能够
在并不是构思对象实际项目标前提下而平昔利用对象下的方法

村办变量和村办方法

在python中用双下划线开始的秘技将品质隐敝起来(设置成私有的)

  多态指的是蓬蓬勃勃致种/类东西的不等造型

3.封装:

【封装】

         隐藏对象的性情和贯彻细节,仅对外提供公共访谈情势。

【好处】 

  1. 将调换隔开分离; 

  2. 造福使用;

  3. 拉长复用性; 

  4. 巩固安全性;

【封装原则】

      1. 将无需对外提供的剧情都掩藏起来;

      2. 把品质都掩藏,提供公共措施对其访谈。

3、怎么样用多态

动物有两种样子:人,狗,猪

图片 27图片 28

import abc
class Animal(metaclass=abc.ABCMeta): #同一类事物:动物
    @abc.abstractmethod
    def talk(self):
        pass

class People(Animal): #动物的形态之一:人
    def talk(self):
        print('say hello')

class Dog(Animal): #动物的形态之二:狗
    def talk(self):
        print('say wangwang')

class Pig(Animal): #动物的形态之三:猪
    def talk(self):
        print('say aoao')

Animal

文本有四种造型:文本文件,可实践文件

图片 29图片 30

import abc
class File(metaclass=abc.ABCMeta): #同一类事物:文件
    @abc.abstractmethod
    def click(self):
        pass

class Text(File): #文件的形态之一:文本文件
    def click(self):
        print('open file')

class ExeFile(File): #文件的形态之二:可执行文件
    def click(self):
        print('execute file')

File

PS:

1.空洞基类是不可能实例化的

2.后续抽象基类的类,必需重写其抽象父类中的抽象方法

个人变量

#其实这仅仅这是一种变形操作
#类中所有双下划线开头的名称如__x都会自动变形成:_类名__x的形式:

class A:
    __N=0 #类的数据属性就应该是共享的,但是语法上是可以把类的数据属性设置成私有的如__N,会变形为_A__N
    def __init__(self):
        self.__X=10 #变形为self._A__X
    def __foo(self): #变形为_A__foo
        print('from A')
    def bar(self):
        self.__foo() #只有在类内部才可以通过__foo的形式访问到.

#A._A__N是可以访问到的,即这种操作并不是严格意义上的限制外部访问,仅仅只是一种语法意义上的变形

 

这种自发性别变化形的特点:

1.类中定义的__x只可以在里面采取,如self.__x,**援引的正是变形的结果**。

2.这种变形其实正是针对外部的变形,在外表是心余力绌透过__x这么些名字访谈到的。

3.在子类定义的__x不会覆盖在父类定义的__x,因为子类中变产生了:_子类名__x,而父类中变产生了:_父类名__x,即双下滑线起头的质量在继续给子类时,子类是回天乏术掩没的。**

 

这种变形须求小心的主题材料是:

1.这种体制也并未当真意义上限制我们从外表直接访谈属性,知道了类名和质量名就可以拼知名字:_类名__性子,然后就可以访谈了,如a._A__N

2.变形的进程只在类的个中生效,在概念后的赋值操作,不会变形

图片 31

2.为什么要用多态

村办变量和村办方法:

在python中用双下划线开首的法子将质量隐敝起来(设置成私有的)

#其实这仅仅这是一种变形操作
#类中所有双下划线开头的名称如__x都会自动变形成:_类名__x的形式:

class A:
    __N=0 #类的数据属性就应该是共享的,但是语法上是可以把类的数据属性设置成私有的如__N,会变形为_A__N
    def __init__(self):
        self.__X=10 #变形为self._A__X
    def __foo(self): #变形为_A__foo
        print('from A')
    def bar(self):
        self.__foo() #只有在类内部才可以通过__foo的形式访问到.

#A._A__N是可以访问到的,即这种操作并不是严格意义上的限制外部访问,仅仅只是一种语法意义上的变形

这种自动变形的特点:

1.类中定义的__x只好在里面使用,如self.__x,**援引的正是变形的结果**。

2.这种变形其实正是本着外界的变形,在外界是力无法支通过__x这几个名字访问到的。

3.在子类定义的__x不会覆盖在父类定义的__x,因为子类中变产生了:_子类名__x,而父类中变形成了:_父类名__x,即双下滑线开头的品质在后续给子类时,子类是无法覆盖的。**

这种变形须要小心的题目是:

1.这种机制也并不曾真的意义上限定大家从表面直接待上访谈属性,知道了类名和质量名就能够拼有名字:_类名__属性,然后就足以访谈了,如a._A__N

2.变形的进度只在类的概念是发出二遍,在概念后的赋值操作,不会变形

4、多态性

1.什么样是多态动态绑定(在继续的背景下使用时,又叫做多态性)

多态性是指在不思量实力类型的事态下使用实例

图片 32图片 33

在面向对象方法中一般是这样表述多态性:向不同的对象发送同一条消息(!!!obj.func():是调用了obj的方法func,又称为向obj发送了一条消息func),不同的对象在接收时会产生不同的行为(即方法)。也就是说,每个对象可以用自己的方式去响应共同的消息。所谓消息,就是调用函数,不同的行为就是指不同的实现,即执行不同的函数。

比如:老师.下课铃响了(),学生.下课铃响了(),老师执行的是下班操作,学生执行的是放学操作,虽然二者消息一样,但是执行的效果不同

解释

2.为什么要用多态性(多态性的益处)

  • 充实了前后相继的眼观六路

    以不改变应万变,无论对象出没无定,使用者都是意气风发律种情势去调用

  • 日增了前后相继的可扩大性

    透过世袭animal类创立了三个新的类,使用者不需求改善自身的代码,依然用func(animal卡塔尔(قطر‎去调用

图片 34图片 35

>>> class Cat(Animal): #属于动物的另外一种形态:猫
...     def talk(self):
...         print('say miao')
... 
>>> def func(animal): #对于使用者来说,自己的代码根本无需改动
...     animal.talk()
... 
>>> cat1=Cat() #实例出一只猫
>>> func(cat1) #甚至连调用方式也无需改变,就能调用猫的talk功能
say miao

'''
这样我们新增了一个形态Cat,由Cat类产生的实例cat1,使用者可以在完全不需要修改自己代码的情况下。使用和人、狗、猪一样的方式调用cat1的talk方法,即func(cat1)
'''

演示代码

 

3.红鸭类型

Python中崇尚绿头鸭类型(要是看起来像,叫声音图像何况走起路像潜水鸭,那么它正是秋沙鸭)

由此持续完结的多态性,具有强耦合性;

绿头鸭类型,通过创设贰个外观和表现像,但与原类型毫非亲非故系的崭新对象,具备松耦合性;

图片 36图片 37

#其实大家一直在享受着多态性带来的好处,
#比如Python的序列类型有多种形态:字符串,列表,元组,多态性的体现
#
#str,list,tuple都是序列类型
s=str('hello')
l=list([1,2,3])
t=tuple((4,5,6))

#我们可以在不考虑三者类型的前提下使用s,l,t
s.__len__()
l.__len__()
t.__len__()

len(s)
len(l)
len(t)

示范代码

 

村办方法

3.在延续中,父类假设不想让子类覆盖本人的不二秘籍,能够将艺术定义为私有的

这种变形必要注意的标题是:

1.这种机制也并不曾真的意义上限定我们从表面直接待上访谈属性,知道了类名和总体性名就能够拼闻名字:_类名__属性,然后就能够访谈了,如a._A__N

2.变形的历程只在类的里边生效,在概念后的赋值操作,不会变形

图片 38

  多态性:在多态的背景下,能够在毫无考虑对象实际项目标前提下而直接使用对象

个体方法:

**3.在世襲中,父类假使不想让子类覆盖本人的章程,能够将艺术定义为私有的**

 

#正常情况
>>> class A:
...     def fa(self):
...         print('from A')
...     def test(self):
...         self.fa()
... 
>>> class B(A):
...     def fa(self):
...         print('from B')
... 
>>> b=B()
>>> b.test()
from B


#把fa定义成私有的,即__fa
>>> class A:
...     def __fa(self): #在定义时就变形为_A__fa
...         print('from A')
...     def test(self):
...         self.__fa() #只会与自己所在的类为准,即调用_A__fa
... 
>>> class B(A):
...     def __fa(self):
...         print('from B')
... 
>>> b=B()
>>> b.test()
from A

民用方法

3.在世袭中,父类假设不想让子类覆盖自身的办法,能够将艺术定义为私有的

#正常情况
>>> class A:
...     def fa(self):
...         print('from A')
...     def test(self):
...         self.fa()
... 
>>> class B(A):
...     def fa(self):
...         print('from B')
... 
>>> b=B()
>>> b.test()
from B


#把fa定义成私有的,即__fa
>>> class A:
...     def __fa(self): #在定义时就变形为_A__fa
...         print('from A')
...     def test(self):
...         self.__fa() #只会与自己所在的类为准,即调用_A__fa
... 
>>> class B(A):
...     def __fa(self):
...         print('from B')
... 
>>> b=B()
>>> b.test()
from A

3.怎么着用多态

包装与扩充性:

封装在于分明区分内外,使得类完成者可以修正封装内的事物而不影响外界调用者的代码;而外界使用用者只略知生龙活虎二多少个接口(函数卡塔尔,只要接口(函数)名、参数不改变,使用者的代码永久不供给改动。这就提供叁个杰出的合营根底——大概说,只要接口那么些底蕴约定不改变,则代码改造不值一提。

#类的设计者
class Room:
    def __init__(self,name,owner,width,length,high):
        self.name=name
        self.owner=owner
        self.__width=width
        self.__length=length
        self.__high=high
    def tell_area(self): #对外提供的接口,隐藏了内部的实现细节,此时我们想求的是面积
        return self.__width * self.__length


#使用者
>>> r1=Room('卧室','egon',20,20,20)
>>> r1.tell_area() #使用者调用接口tell_area


#类的设计者,轻松的扩展了功能,而类的使用者完全不需要改变自己的代码
class Room:
    def __init__(self,name,owner,width,length,high):
        self.name=name
        self.owner=owner
        self.__width=width
        self.__length=length
        self.__high=high
    def tell_area(self): #对外提供的接口,隐藏内部实现,此时我们想求的是体积,内部逻辑变了,只需求修该下列一行就可以很简答的实现,而且外部调用感知不到,仍然使用该方法,但是功能已经变了
        return self.__width * self.__length * self.__high


#对于仍然在使用tell_area接口的人来说根本无需改动自己的代码,就可以用上新功能

打包与扩张性

封装在于显明区分内外,使得类实现者能够改善封装内的东西而不影响外界调用者的代码;而外界使用用者只略知大器晚成二二个接口(函数卡塔尔(英语:State of Qatar),只要接口(函数)名、参数不改变,使用者的代码恒久不要求改换。那就提供多少个能够的通力合作底蕴——可能说,只要接口这一个底子约定不变,则代码退换无足轻重。

#类的设计者
class Room:
    def __init__(self,name,owner,width,length,high):
        self.name=name
        self.owner=owner
        self.__width=width
        self.__length=length
        self.__high=high
    def tell_area(self): #对外提供的接口,隐藏了内部的实现细节,此时我们想求的是面积
        return self.__width * self.__length


#使用者
>>> r1=Room('卧室','egon',20,20,20)
>>> r1.tell_area() #使用者调用接口tell_area


#类的设计者,轻松的扩展了功能,而类的使用者完全不需要改变自己的代码
class Room:
    def __init__(self,name,owner,width,length,high):
        self.name=name
        self.owner=owner
        self.__width=width
        self.__length=length
        self.__high=high
    def tell_area(self): #对外提供的接口,隐藏内部实现,此时我们想求的是体积,内部逻辑变了,只需求修该下列一行就可以很简答的实现,而且外部调用感知不到,仍然使用该方法,但是功能已经变了
        return self.__width * self.__length * self.__high


#对于仍然在使用tell_area接口的人来说,根本无需改动自己的代码,就可以用上新功能
>>> r1.tell_area()

 

  Animal()  #父类只是用来确立标准的,无法用来实例化,更无需兑现内部的措施

property属性:

图片 39图片 40

例一:BMI指数(bmi是计算而来的,但很明显它听起来像是一个属性而非方法,如果我们将其做成一个属性,更便于理解)

成人的BMI数值:
过轻:低于18.5
正常:18.5-23.9
过重:24-27
肥胖:28-32
非常肥胖, 高于32
  体质指数(BMI)=体重(kg)÷身高^2(m)
  EX:70kg÷(1.75×1.75)=22.86

例子1

图片 41图片 42

class People:
    def __init__(self,name,weight,height):
        self.name=name
        self.weight=weight
        self.height=height
    @property
    def bmi(self):
        return self.weight / (self.height**2)

p1=People('egon',75,1.85)
print(p1.bmi)

例子2

图片 43图片 44

import math
class Circle:
    def __init__(self,radius): #圆的半径radius
        self.radius=radius

    @property
    def area(self):
        return math.pi * self.radius**2 #计算面积

    @property
    def perimeter(self):
        return 2*math.pi*self.radius #计算周长

c=Circle(10)
print(c.radius)
print(c.area) #可以向访问数据属性一样去访问area,会触发一个函数的执行,动态计算出一个值
print(c.perimeter) #同上
'''
输出结果:
314.1592653589793
62.83185307179586
'''

例子3

#瞩目:那个时候的特色area和perimeter不可能被赋值
c.area=3 #为特性area赋值
''' 抛出极度: AttributeError: can't set attribute

 

 

怎么要用property

将二个类的函数定义成特征今后,对象再去行使的时候obj.name,根本不能察觉本身的name是施行了二个函数然后总结出来的,这种特点的应用方式遵照了联合访谈的原则

而外,看下

ps:面向对象的封装有三种方式:
【public】
这种其实就是不封装,是对外公开的
【protected】
这种封装方式对外不公开,但对朋友(friend)或者子类(形象的说法是“儿子”,但我不知道为什么大家 不说“女儿”,就像“parent”本来是“父母”的意思,但中文都是叫“父类”)公开
【private】
这种封装对谁都不公开

 

图片 45

python并从未在语法上把它们四个内建到协调的class机制中,在C 里平常会将装有的具备的多少都安装为私有的,然后提供set和get方法(接口)去设置和获得,在python中通过property方法能够实现

图片 46图片 47

class Foo:
    def __init__(self,val):
        self.__NAME=val #将所有的数据属性都隐藏起来

    @property
    def name(self):
        return self.__NAME #obj.name访问的是self.__NAME(这也是真实值的存放位置)

    @name.setter
    def name(self,value):
        if not isinstance(value,str):  #在设定值之前进行类型检查
            raise TypeError('%s must be str' %value)
        self.__NAME=value #通过类型检查后,将值value存放到真实的位置self.__NAME

    @name.deleter
    def name(self):
        raise TypeError('Can not delete')

f=Foo('egon')
print(f.name)
# f.name=10 #抛出异常'TypeError: 10 must be str'
del f.name #抛出异常'TypeError: Can not delete'

View Code

贰个静态属性property本质就是得以完成了get,set,delete三种形式

图片 48图片 49

class Foo:
    @property
    def AAA(self):
        print('get的时候运行我啊')

    @AAA.setter
    def AAA(self,value):
        print('set的时候运行我啊')

    @AAA.deleter
    def AAA(self):
        print('delete的时候运行我啊')

#只有在属性AAA定义property后才能定义AAA.setter,AAA.deleter
f1=Foo()
f1.AAA
f1.AAA='aaa'
del f1.AAA

View Code

图片 50图片 51

class Foo:
    def get_AAA(self):
        print('get的时候运行我啊')

    def set_AAA(self,value):
        print('set的时候运行我啊')

    def delete_AAA(self):
        print('delete的时候运行我啊')
    AAA=property(get_AAA,set_AAA,delete_AAA) #内置property三个参数与get,set,delete一一对应

f1=Foo()
f1.AAA
f1.AAA='aaa'
del f1.AAA

View Code

图片 52图片 53

class Goods:

    def __init__(self):
        # 原价
        self.original_price = 100
        # 折扣
        self.discount = 0.8

    @property
    def price(self):
        # 实际价格 = 原价 * 折扣
        new_price = self.original_price * self.discount
        return new_price

    @price.setter
    def price(self, value):
        self.original_price = value

    @price.deleter
    def price(self):
        del self.original_price


obj = Goods()
obj.price         # 获取商品价格
obj.price = 200   # 修改商品原价
print(obj.price)
del obj.price     # 删除商品原价

View Code

 

property属性

何以是特色property

property是黄金时代种格外的天性,访谈它时会施行生机勃勃段功能(函数)然后重回值

例一:BMI指数(bmi是计算而来的,但很明显它听起来像是一个属性而非方法,如果我们将其做成一个属性,更便于理解)

成人的BMI数值:
过轻:低于18.5
正常:18.5-23.9
过重:24-27
肥胖:28-32
非常肥胖, 高于32
  体质指数(BMI)=体重(kg)÷身高^2(m)
  EX:70kg÷(1.75×1.75)=22.86

class People:
    def __init__(self,name,weight,height):
        self.name=name
        self.weight=weight
        self.height=height
    @property   #让最下面的pl.bmi省去了后面的括号,变成了print(pl.bmi)

  def bmi(self): 
    return self.weight / (self.height**2) 

p1=People('egon',75,1.85) 
print(p1.bmi)

import math
class Circle:
    def __init__(self,radius): #圆的半径radius
        self.radius=radius

    @property  #property  实际上是把类的方法变成了属性,所以类调用属性不需要加括号  c.area
    def area(self):   #类调用方法要加括号  c.area()
        return math.pi * self.radius**2 #计算面积

    @property
    def perimeter(self):
        return 2*math.pi*self.radius #计算周长

c=Circle(10)
print(c.radius)
print(c.area) #可以向访问数据属性一样去访问area,会触发一个函数的执行,动态计算出一个值
print(c.perimeter) #同上
'''
输出结果:
314.1592653589793
62.83185307179586
'''

 

#注意:此时的特性area和perimeter不能被赋值
c.area=3 #为特性area赋值
'''
抛出异常:
AttributeError: can't set attribute
'''

为啥要用property

将三个类的函数定义成特色今后,对象再去接纳的时候obj.name,根本无法察觉本身的name是施行了二个函数然后计算出来的,这种天性的利用方式根据了联合访谈的规范

除了那个之外,看下

ps:面向对象的封装有三种方式:
【public】
这种其实就是不封装,是对外公开的
【protected】
这种封装方式对外不公开,但对朋友(friend)或者子类(形象的说法是“儿子”,但我不知道为什么大家 不说“女儿”,就像“parent”本来是“父母”的意思,但中文都是叫“父类”)公开
【private】
这种封装对谁都不公开

python并不以前在语法上把它们多个内建到谐和的class机制中,在C 里日常会将有着的具有的数目都安装为个体的,

接下来提供set和get方法(接口)去设置和获得,在python中经过property方法能够兑现   备考:不太明白

class Foo:
    def __init__(self,val):
        self.__NAME=val #将所有的数据属性都隐藏起来

    @property
    def name(self):
        return self.__NAME #obj.name访问的是self.__NAME(这也是真实值的存放位置)

    @name.setter
    def name(self,value):
        if not isinstance(value,str):  #在设定值之前进行类型检查
            raise TypeError('%s must be str' %value)
        self.__NAME=value #通过类型检查后,将值value存放到真实的位置self.__NAME

    @name.deleter
    def name(self):
        raise TypeError('Can not delete')

f=Foo('egon')
print(f.name)
# f.name=10 #抛出异常'TypeError: 10 must be str'
del f.name #抛出异常'TypeError: Can not delete'

三个静态属性property本质就是贯彻了get,set,delete三种方法   (查看,改过,删除)备注:不太知道

class Foo:
    @property
    def AAA(self):
        print('get的时候运行我啊')

    @AAA.setter
    def AAA(self,value):
        print('set的时候运行我啊')

    @AAA.deleter
    def AAA(self):
        print('delete的时候运行我啊')

#只有在属性AAA定义property后才能定义AAA.setter,AAA.deleter
f1=Foo()
f1.AAA
f1.AAA='aaa'
del f1.AAA

class Goods:

    def __init__(self):
        # 原价
        self.original_price = 100
        # 折扣
        self.discount = 0.8

    @property
    def price(self):
        # 实际价格 = 原价 * 折扣
        new_price = self.original_price * self.discount
        return new_price

    @price.setter
    def price(self, value):
        self.original_price = value

    @price.deleter
    def price(self):
        del self.original_price


obj = Goods()
obj.price         # 获取商品价格
obj.price = 200   # 修改商品原价
print(obj.price)
del obj.price     # 删除商品原价
 1 import abc
 2 
 3 
 4 class Animal(metaclass=abc.ABCMeta):
 5     @abc.abstractmethod
 6     def speak(self):
 7         pass
 8 
 9     @abc.abstractmethod
10     def run(self):
11         pass
12 
13 
14 
15 class People(Animal):
16     def speak(self):
17         print('say hello')
18 
19     def run(self):
20         pass
21 
22 
23 class Dog(Animal):
24     def speak(self):
25         print('汪汪汪')
26 
27     def run(self):
28         pass
29 
30 
31 class Pig(Animal):
32     def speak(self):
33         print('哼哼哼')
34 
35     def run(self):
36         pass
37 
38 
39 obj1 = People()
40 obj2 = Dog()
41 obj3 = Pig()

classmethod   八个格局成为类中的方法,那么些艺术间接就可以被调用

class Classmethod_Demo():
    role = 'dog'

    @classmethod
    def func(cls):
        print(cls.role)

Classmethod_Demo.func()

Python推崇的是树鸭类型,只要你叫的响声音图像赤麻鸭,况且你走路的轨范也像赤麻鸭,那你就是秋沙鸭

staticmethod   在一同面向对象的前后相继中,借使二个函数既和队象没提到也和类无妨,那么就用staticmethod将以此办法成为静态方法

class Staticmethod_Demo():
    role = 'dog'

    @staticmethod
    def func():
        print("当普通方法用")

Staticmethod_Demo.func()

类措施和静态方法能够被类调用

目标足以调用类方法和静态方法,通常用类名调用

类措施  有叁个暗许参数  cls    代表那个类  cls

 

 1 class Disk:
 2     def read(self):
 3         print('Disk read')
 4 
 5     def write(self):
 6         print('Disk write')
 7 
 8 
 9 class Memory:
10     def read(self):
11         print('Mem read')
12 
13     def write(self):
14         print('Mem write')
15 
16 
17 class Cpu:
18     def read(self):
19         print('Cpu read')
20 
21     def write(self):
22         print('Cpu write')
23 
24 
25 obj1 = Disk()
26 obj2 = Memory()
27 obj3 = Cpu()
28 
29 obj1.read()
30 obj2.read()
31 obj3.read()

 

面向对象-封装

1.如何是包装

  装: 往容器/名称空间里存入名字

  封: 代表将贮存于名称空间中的名字给藏起来,这种隐形对外不对内

2.为啥要卷入

  封装数据属性:

    将数据属性隐敝起来,类外就无法直接操作属性,要求类内部开拓二个接口,让外部的使用能够直接地操作属性,能够在接口钦赐制恣意的垄断逻辑,进而严控使用者对质量的操作

 1 class People:
 2     def __init__(self, name, age):
 3         self.__name = name
 4         self.__age = age
 5 
 6     def tell_info(self):
 7         print('<name:%s age:%s>' % (self.__name, self.__age))
 8 
 9     def set_info(self, name, age):
10         if type(name) is not str:
11             print('名字必须是str类型傻叉')
12             return
13         if type(age) is not int:
14             print('年龄必须是int类型傻叉')
15             return
16         self.__name = name
17         self.__age = age
18 
19 
20 obj = People('egon', 18)
21 obj.set_info('EGON', '18')
22 obj.tell_info()

  封装函数属性: 隔离复杂度

 1 class ATM:
 2     def __card(self):
 3         print('插卡')
 4 
 5     def __auth(self):
 6         print('用户认证')
 7 
 8     def __input(self):
 9         print('输入取款金额')
10 
11     def __print_bill(self):
12         print('打印账单')
13 
14     def __take_money(self):
15         print('取款')
16 
17     def withdraw(self):
18         self.__card()
19         self.__auth()
20         self.__input()
21         self.__print_bill()
22         self.__take_money()
23 
24 
25 a = ATM()
26 a.withdraw()

3.哪些封装

  在类内定义的习性前加__开头(没有__结尾)

  总结:

    1. __起始的品质达成的隐身仅仅只是风姿浪漫种语法意义上的变形,并不会真正约束类外界的探访

    2. 该变形操作只在类定义阶段检查实验语法时发生壹次,类定义阶段之后新扩大的__起首的品质并不会变形

    3. 倘诺父类不想让子类覆盖本人的属性,能够在性质前加__开头

 1 class Foo:
 2     def __f1(self):  # _Foo__f1
 3         print('Foo.f1')
 4 
 5     def f2(self):
 6         print('Foo.f2')
 7         self.__f1()  # obj._Foo__f1()
 8 
 9 
10 class Bar(Foo):
11     def __f1(self):  # _Bar__f1
12         print('Bar.f1')
13 
14 
15 obj = Bar()
16 
17 >>>Foo.f2
18 >>>Foo.f1

 

面向对象-property

property装饰器是用来将类内的函数属性伪装成数据属性

 1 class People:
 2     def __init__(self, name):
 3         self.__name = name
 4 
 5     @property
 6     def name(self):
 7         return '<名字:%s>' % self.__name
 8 
 9     @name.setter
10     def name(self, obj):
11         if type(obj) is not str:
12             print('name必须为str类型')
13             return
14         self.__name = obj
15 
16     @name.deleter
17     def name(self):
18         print('不让删')
19 
20 obj = People('egon')
21 del obj.name
22 print(obj.__dict__)

 

本文由pc28.am发布于计算机编程,转载请注明出处:python面向对象三大特征,面向对象

上一篇:修饰符的用法,修饰符的用法详整 下一篇:没有了
猜你喜欢
热门排行
精彩图文
  • python面向对象三大特征,面向对象
    python面向对象三大特征,面向对象
    面向对象-组合 风流罗曼蒂克、面向进度与面向对象的简要介绍 一、继承 大器晚成 什么是多态动态绑定(在这里起彼伏的背景下行使时,一时也称得上多
  • HttpRuntime的认知与抓好明白,异步HTTP乞请操作
    HttpRuntime的认知与抓好明白,异步HTTP乞请操作
    一、说明 上边最早介绍HttpRuntime的Web.config里的构造 1卡塔尔(英语:State of Qatar) 那些类 是本身 在安分守己项目中,优化驱除实际难题时,不参照第三方代码
  • 那些年【深入.NET平台和C#编程】
    那些年【深入.NET平台和C#编程】
    一、深入.NET框架 ArrayList (非泛型集合  using System.Collections;) public void Text1(){ ArrayList al = new ArrayList (); al.Add ("刘德化");       //添加元素 al.Add ("张学友
  • 碰着搭建
    碰着搭建
    Appium是移动端的自动化测试工具,类似于前面所说的Selenium,利用它可以驱动Android、iOS等设备完成自动化测试,比如模拟点击、滑动、输入等操作,其官方
  • Django中的CBV和FBV示例介绍
    Django中的CBV和FBV示例介绍
    Django中的CBV和FBV Django中的CBV和FBV示例介绍,djangocbvfbv示例 前言 本文主要给大家介绍了关于Django中CBV和FBV的相关内容,分享出来供大家参考学习,下面话不