第十六章: 面向对象 - 继承和多态

01 - 面向对象 - 继承简介

1.提高了代码的复用性 2.让类与类之间产生关系,有了这个关系,才有了多态的特性

class Person():

    name = ''
    age = ''

class Doctor():

    name = ''
    age = ''

    def zhibing(self):

        print('治疗病人')

class soldier():
    name = ''
    age = ''

    def baowei(self):
        print('保卫国家')

1.继承的简介
1.提高了代码的复用性 2.让类与类之间产生关系,有了这个关系,才有了多态的特性
3.继承也是面向对象的三大特征之一

定义一个动物类

如何能让这个当前的动物类实现全部的功能
1.直接修改这个动物类,在这个类中添加我们需要的功能
2.可以直接创建一个新类
3.直接从动物类中继承它的属性和方法
在创建类的时候,如果我们省略父类则默认父类为object
所有类都继承object,object是所有类的父类

class Animal:

    def run(self):
        print('动物在跑')

    def sleep(self):
        print('动物在睡觉')

    # def speak(self):
    #     print('动物会叫')

class cat():

    def run(self):
        print('猫在跑')

    def sleep(self):
        print('猫在睡觉')

    def speak(self):
        print('猫在叫')

class cat(Animal):

    def run(self):

        print('猫在跑')

    def speak(self):

        print('喵喵喵')


# a = Animal()
c = cat()
# print(c)
c.run()
# c.sleep()
# c.speak()

# r = isinstance(c,Animal)
# issubclass()

class Person():
    pass

print(issubclass(cat,Animal))
print(issubclass(Animal,object))
print(issubclass(Person,object))
# print(issubclass(print,object))   # 不能这么写
print(isinstance(print,object))

>>>
猫在跑
True
True
True
True

2. - 面向对象 - 重写


class Animal:

    def run(self):
        print('动物在跑')

    def sleep(self):
        print('动物在睡觉')

    # def speak(self):
    #     print('动物会叫')

class cat():

    def run(self):
        print('猫在跑')

    def sleep(self):
        print('猫在睡觉')

    def speak(self):
        print('猫在叫')

# 如果子类中有父类同名的方法,则通过子类的实例去调用该方法时, 会调用子类的方法而不是父类的方法,这个特点也称之为我们所说的方法重写(覆盖)
class cat(Animal):

    # def run(self):
    #
    #     print('猫在跑')

    def speak(self):

        print('喵喵喵')


# a = Animal()
c = cat()
# print(c)
# c.run()
# c.sleep()
# c.speak()


# 当我们调用一个对象的方法时
# 会优先去当前对象中去寻找是否有该方法,如果有则直接调用
# 如果没有,则去当前对象的父类中寻找,如果父类中有则直接调用
# 如果没有,则去父类对象中的父类中去寻找,以此类推,直到找到object,如果没有则报错
class A(object):

    def text(self):

        print('AAA')

class B(A):

    def text(self):

        print('BBB')

class C(B):
    def text(self):

        print('CCC')

c = C()

c.text()


>>>

CCC

03.面向对象 - supper()

class Animal:

    def __init__(self,name):

        self._name = name

    def run(self):
        print('动物在跑')

    def sleep(self):
        print('动物在睡觉')

    @property
    def name(self):
        return self._name

    @name.setter
    def name(self,name):
        self._name = name
# 三、supper()
# 父类中的所有方法都会被子类继承,包括特殊方法
class cat(Animal):

    # 我希望可以直接调用父类中的__init__方法来初始化父类中的属性
    # supper()可以获得当前类的父类
    # 通过supper()返回对象调应父类方法时,不需要传递self
    def __init__(self,name,age):
        Animal.__init__(self,name)  # 或者 supper().__init__(name)
        # self._name = name
        self._age = age

    def run(self):
        print('猫在跑')

    def speak(self):
        print('喵喵喵')

    @property
    def age(self):
        return self._age

    @age.setter
    def age(self, age):
        self._age = age


c = cat('波斯猫',44)
c.name = '加菲猫'

print(c.name)
print(c.age)

>>>
加菲猫
44

04 - 面向对象 - 多重继承

Python中支持多重继承,也就是我们可以为一个类同时制定多个父类
bases
语法 类名 .__bases__可以获取当前类所有的父类

class A(object):

    def text(self):

        print('AAA')

class B(object):

    def text(self):

        print('BBB')

class C(B):

    pass

print(C.__bases__)   # 打印结果是一个元组 打印结果:(<class '__main__.B'>,)
print(B.__bases__)   # 打印结果是一个元组 打印结果:(<class 'object'>,)


class A(object):

    def text(self):

        print('AAA')

class B(object):

    def text(self):

        print('BBB')

class C(A,B):

    pass

print(C.__bases__)  #打印结果是两个元组 打印结果:(<class '__main__.A'>, <class '__main__.B'>)


# 我们在开发的时候尽量不要用多重继承,原因是增加我们代码的复杂程度
# 如果多个父类中出现重名的方法,则会先在第一个父类中寻找,然后再找第二个,再找第三个,后边会覆盖前边

class A(object):

    def text(self):

        print('AAA')

class B(object):

    def text2(self):

        print('BBB')

class C(A,B):

    pass

c = C()
c.text()   # AAA
c.text2()  # BBB

# 05. - 多态


多态也是面向对象的三大特性之一
一个对象可以以不同的邢台去呈现

鸭子类型:
如果有一个东西 走路像鸭子 ,叫声像鸭子,那么它就是鸭子

```python
class A:

    def __init__(self,name):

        self._nmae = name


    @property
    def name(self):
        return self._name

    @name.setter
    def name(self,name):
        self._name = name


class B:

    def __init__(self, name):
        self._nmae = name

    def __len__(self):
        return 10

    @property
    def name(self):
        return self._name

    @name.setter
    def name(self, name):
        self._name = name

class C:
    pass

a = A('葫芦娃')
b = B('钢铁侠')
c = C()

def say(obj):

    print('你好 %s'%obj.name)


def say2(obj):

    # 做类型检查
    # 违反了多态的函数只适用于一种类型的对象,无法处理其他诶行的对象,这样会导致函数的适用性非常差
    if isinstance(obj,A):

        print('你好 %s'%obj.name)

# say(c)
# say2(b)  # Process finished with exit code 0

# len()
# 之所以一个对象能够通过len()函数获取长度,是因为对象中具有一个特殊方法__len__
lst = [1,2,3]
s = 'Python'
# print(len(lst))

# print(len(s))

print(len(b))   # 10
print(len(c))   # TypeError: object of type 'C' has no len()
                # c这个对象没有len()这个函数

# 面相对象的三大 特征 :    封装:确保对象中数据的安全  继承;保证了对象的可扩展  多态:保证了程序的灵活性

06. - 面向对象 - 属性和方法

# 类方法和实例方法的区别:实例方法第一个参数是self,类方法第一个参数是cls
class A(object):

    # 类属性  直接在类中第一个属性就是类属性
    # 类属性可以通过类本身或者是类的实例访问
    # 类属性  只能通过类对象来修改,无法通过实例对象来修改
    count = 0

    # 实例属性,通过实例对象添加的属性叫做实例属性
    # 实例属性  只能通过实例对象来访问和修改,类对象无法访问和修改

    def __init__(self):

        self.name = '葫芦娃'

    # 实例方法
    # 在类中定义,以self为参数的方法都是实例方法
    # 实例方法在调用时,Python会将调用的对象作为self传入
    #当通过类调用时,不会自动传入self
    def text(self):

        print('这是text方法',self)

    # 类方法
    # 在类的内部使用 @classmethod 来修饰的方法叫做类方法
    # 类方法第一个参数是cls  会被自动上传 cls就是当前的类对象
    @classmethod
    def text2(cls):
        print('这是text2方法',cls)
        print(cls.count)

    # 静态方法
    # 在类中内部使用@staticmethod 来修饰的方法属于静态方法
    # 静态方法不需要指定任何默认的参数,静态方法可以通过类和实例去调用
    @staticmethod
    def text3():

        print('text3执行了')


a = A()

# a.count = 5
# A.count = 5
# print('A',A.name) # AttributeError: type object 'A' has no attribute 'name'
print('a',a.name)   #  a 葫芦娃

a.text()    # 这是text方法 <__main__.A object at 0x000001E4EA0C0BE0>
A.text(a)   # 这是text方法 <__main__.A object at 0x000001E4EA0C0BE0>  # a.text() 等价于 A.text(a)

A.text2()  # 这是text2方法 <class '__main__.A'>
            # 0
a.text2()  # 这是text2方法 <class '__main__.A'> # A.text2() 等价于 a.text2()
            # 0

A.text3()  # text3执行了
a.text3()  # text3执行了
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值