日韩久久久精品,亚洲精品久久久久久久久久久,亚洲欧美一区二区三区国产精品 ,一区二区福利

python面向對象基礎(三)

系統 1760 0

本節開始,我們將討論面向對象編程的三大特征:封裝、繼承和多態。下面,我們將由簡至難,依次討論封裝、繼承、多態。

一. 封裝?enclosure

  • 封裝:指隱藏類的實現細節,讓使用者不用關心這些細節;
  • 目的:讓使用者通過盡可能少的方法(或屬性)操作對象;
  • 如何封裝:通過私有屬性和方法;
  • 私有屬性和方法:
  1. 以雙下劃線'__'開頭,不以雙下劃線結尾的標識符為私有成員;
  2. 私有成員只能用此類的方法進行訪問和修改
  • 擴展:了解java的讀者可能知道,java中使用了private、default、protected、public關鍵字,實現了更豐富的封裝;
  • 示例:
            
              class A:
    """用私有屬性和私有方法封裝屬性和方法"""
    __dd = 300

    def __init__(self):
        # 創建私有屬性,此屬性在類外無法訪問
        self.__e = 100

    @staticmethod
    # 私有方法
    def __en():
        print('私有方法__en被調用!')

    @classmethod
    def get__dd(cls):
        print("私有的類變量__dd:{}".format(cls.__dd))

    def info(self):
        print('A的實例方法info訪問私有屬性__e:', self.__e)
        # 調用私有方法
        self.__en()


if __name__ == "__main__":
    a = A()
    a.info()
    a.__class__.get__dd()

    # print(a.__e) #AttributeError: 'A' object has no attribute '__e'
    # print(a.__en()) #AttributeError: 'A' object has no attribute '_en'

    # 創建新變量(屬性)
    a.__e = 'hello'
    print(a.__e)
    print(a.__dict__)

            
          

運行結果:

? ? python面向對象基礎(三)_第1張圖片

二.?繼承 inheritance 和 派生 derived

  • 什么是繼承/派生:
  1. 繼承是指從已有的類中派生出新的類,新類具有原類的行為,并能擴展新的行為;
  2. 派生類就是從一個已有的類衍生出新的類,在新的類上可以添加新的屬性和行為;
  • 作用:
  1. 用繼承派生機制,可以將一些共有功能加在基類中,實現代碼共享;(共有的屬性和方法向上提,形成抽象)
  2. 在不改變超類的代碼基礎上改變原有功能
  • 名詞:
  1. 基類 base class / 超類 super class / 父類 father class
  2. 派生類 derived class / 子類

1. 單繼承

  • 語法:

?? ??? ?class 類名( 基類名 ):
?? ??? ??? ?語句塊

  • 說明:單繼承是派生類由一個基類衍生而來的
  • 類的__base__屬性:用來記錄此類的父類
  • 子類對象可以當成父類對象來使用:

? ? ? ? python面向對象基礎(三)_第2張圖片

  • 示例
            
              class Human:
    """此類用來描述人類的共同行為"""
    @staticmethod
    def say(what):
        print('說:', what)

    @staticmethod
    def walk(distance):
        print('走了', distance, '公里')


class Student(Human):
    """描述學生的共同行為"""
    @staticmethod
    def study(subject):
        print('學習', subject)


class Teacher(Student):
    @staticmethod
    def teach(content):
        print('正在教', content)


if __name__ == "__main__":
    h1 = Human()
    h1.say('Today is a good day.')
    h1.walk(5)

    print("#########################")
    s1 = Student()
    s1.say('How are you?')
    s1.walk(5)
    s1.study('Python')

    print("#########################")
    t1 = Teacher()
    t1.say('I am a teacher.')
    t1.walk(3)
    t1.teach('講解繼承派生')
    t1.study('滑冰')

            
          

運行結果:

?? python面向對象基礎(三)_第3張圖片

2. 覆蓋 override

  • 概念:覆蓋是指在有繼承關系的類中,子類中實現了與父類同名的方法,子類實例調用該方法時,實際調用的是子類中覆蓋版本的方法,這種現象被稱為覆蓋;
  • super 函數:
  1. super(type, obj):返回綁定超類的實例(要求obj必須為type類型的實例);
  2. super():返回綁定超類的實例,等同于super(__class__,實例方法的第一個參數self);
  3. super()必須放在方法內調用
  4. 作用:返回綁定超類的實例,用超類的實例來調用其父類的覆蓋方法;
  • 顯示調用父類的構造方法:當子類中實現了__init__方法,父類的構造方法并不會被調用,此時需要顯示調用父類的構造方法:super().__init__(參數)
  • 示例1:在方法內使用super()
            
              class Human:
    def __init__(self, n, a):
        self.name = n
        self.age = a

    def info(self):
        print('name:', self.name)
        print('age:', self.age)


class Student(Human):
    def __init__(self, n, a, s):
        # 顯示調用父類的初始化方法
        super().__init__(n, a)
        self.score = s

    def info(self):
        """# 覆蓋,子類只負責干子類的事情"""
        super().info()
        print('score:', self.score)


if __name__ == "__main__":
    h1 = Human('Alex', 22)
    h1.info()

    s1 = Student('Thomas', 25, 99)
    s1.info()

            
          

示例2:

            
              class A:
    def work(self):
        print('A.work被調用!')


class B(A):
    """用super構造函數來間接調用父類的覆蓋版本的方法"""
    def work(self):
        print('B.work被調用!')

    def super_work(self):
        """此方法先調用一下子類的方法,再調用一下父類的方法"""
        self.work()
        # super().work() #調用父類的work,不能在方法外調用
        # super(B,self).work()
        super(__class__, self).work()


if __name__ == "__main__":
    a = A()
    a.work()

    print("###################")
    b = B()
    b.work()

    # 方法外部,使用super()函數調用B的父類A的work方法
    print("###################")
    super(B, b).work()

    print("###################")
    b.super_work()

            
          

示例2運行結果:

?? python面向對象基礎(三)_第4張圖片

2. 多繼承?multiple inheritance

  • 概念:多繼承是指一個子類繼承自兩個或兩個以上的基類;
  • 語法:class類名(基類名1, 基類名2...);
  • 說明:
  1. 一個子類同時繼承自多個父類,父類中的方法可以同時被繼承下來;
  2. 如果兩個父類中有同名的方法,則在子類中又沒有覆蓋此方法時,調用結果難以確定
  • 問題(缺陷):多繼承可能會有標識符(名字空間)沖突的問題;
  • 多繼承的MRO(Method Resolution Order)問題:
  1. '類'的__mro__屬性:用來記錄屬性或方法的查找順序;
  2. 示例:
            
              class A:
    def m(self):
        print('A.m()')


class B:
    def m(self):
        print('B.m()')


class C:
    def m(self):
        print('C.m()')


class D(A, B, C):
    def m(self):
        super(A, self).m()
        super(B, self).m()
        super().m()
        print('D.m()')


if __name__ == "__mian__":
    d = D()
    d.m()
    print(D.__mro__)

            
          

運行結果:

結果分析: super()函數根據MRO順序來查找方法

類D同時繼承自類A,B, C,且這些類中都有方法m,在調用super時,方法的查找順序是按照D.__mro__屬性指定的順序;在D.m()中首先調用的是super(A, self).m(),A的上一個是B,因此首先打印B.m();同理,super(B, self).m(),B的上一個是C,因此打印C.m()。

3. 用于類的函數:issubclass(cls, class_or_tuple)

  • 判斷一個類是否繼承自其它的類,如果此類是 class 或 tuple 中的一個派生子類,則返回 True ,否則返回 False;
  • 一切類型都是 object 的子類

三.?多態 polymorphic

  • 什么是多態:多態是指在有繼承/派生關系的類中,調用“基類對象的方法”,實際能調用子類的覆蓋方法,這種現象被稱為多態;
  • 說明:
  1. 多態“調用的方法與對象相關”,不與類型相關;
  2. Python全部對象都只有運行時狀態(動態),沒有'C++語言'里的編譯時狀態(靜態)
  • 示例:
            
              class Shape:
    def draw(self):
        print('Shape的draw()被調用')


class Point(Shape):
    def draw(self):
        print('正在畫一個點')


class Circle(Point):
    def draw(self):
        print('正在畫一個圓')


def my_draw(s):
    """示意多態的使用"""
    # s.draw調用誰是在運行時由s的類動態決定
    s.draw()


if __name__ == "__main__":
    my_draw(Shape())
    my_draw(Point())
    my_draw(Circle())

            
          

運行結果:

python面向對象基礎(三)_第5張圖片


更多文章、技術交流、商務合作、聯系博主

微信掃碼或搜索:z360901061

微信掃一掃加我為好友

QQ號聯系: 360901061

您的支持是博主寫作最大的動力,如果您喜歡我的文章,感覺我的文章對您有幫助,請用微信掃描下面二維碼支持博主2元、5元、10元、20元等您想捐的金額吧,狠狠點擊下面給點支持吧,站長非常感激您!手機微信長按不能支付解決辦法:請將微信支付二維碼保存到相冊,切換到微信,然后點擊微信右上角掃一掃功能,選擇支付二維碼完成支付。

【本文對您有幫助就好】

您的支持是博主寫作最大的動力,如果您喜歡我的文章,感覺我的文章對您有幫助,請用微信掃描上面二維碼支持博主2元、5元、10元、自定義金額等您想捐的金額吧,站長會非常 感謝您的哦!!!

發表我的評論
最新評論 總共0條評論
主站蜘蛛池模板: 盈江县| 河津市| 钦州市| 明光市| 新蔡县| 封开县| 乌兰县| 黎城县| 保定市| 阿克陶县| 察隅县| 闻喜县| 望江县| 怀安县| 普安县| 惠东县| 西畴县| 余干县| 江华| 忻城县| 子洲县| 博客| 东阿县| 德保县| 阜城县| 仙居县| 宝丰县| 武胜县| 晋宁县| 新竹市| 河津市| 蓝田县| 武宣县| 延寿县| 长兴县| 丰台区| 苗栗县| 张家界市| 会昌县| 辉县市| 长治县|