<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                合規國際互聯網加速 OSASE為企業客戶提供高速穩定SD-WAN國際加速解決方案。 廣告
                [TOC] ## 初識繼承 **什么是繼承?** 繼承指的是類與類之間的關系,是一種什么“是”什么的關系,繼承的功能之一就是用來解決代碼重用問題 繼承是一種創建新類的方式,在python中,新建的類可以繼承一個或多個父類,父類又稱為基類或超類,新建的類稱為派生類或子類 **python中類的繼承分為:單繼承和多繼承** ~~~ class ParentClass1: #定義父類 pass class ParentClass2: #定義父類 pass class SubClass1(ParentClass1): #單繼承 pass class SubClass2(ParentClass1,ParentClass2): #多繼承用逗號分隔 pass ~~~ **查看繼承** `__base__`只查看從左到右繼承的第一個子類,`__bases__`則是查看所有繼承的父類 ~~~ >>> SubClass1.__bases__ (<class '__main__.ParentClass1'>,) >>> SubClass2.__bases__ (<class '__main__.ParentClass1'>, <class '__main__.ParentClass2'>) ~~~ ### 繼承與抽象 **抽象即抽取類似或者說比較像的部分**。抽象分成兩個層次: 1.將奧巴馬和梅西這倆對象比較像的部分抽取成類(人類); 2.將人,豬,狗這三個類比較像的部分抽取成父類(動物類)。 抽象最主要的作用是劃分類別,可以隔離關注點,降低復雜度. **繼承:是基于抽象的結果,通過編程語言去實現它** 肯定是先經歷抽象這個過程,才能通過繼承的方式去表達出抽象的結構。 ### 繼承與重用性 在開發程序的過程中,定義了一個類A,又想新建立另外一個類B,但是類B的大部分內容與類A的相同時 通過繼承的方式新建類B,讓B繼承A,B會‘遺傳’A的所有屬性(數據屬性和函數屬性),實現代碼重用 ~~~ class Hero: def __init__(self,nickname,aggressivity,life_value): self.nickname=nickname self.aggressivity=aggressivity self.life_value=life_value def move_forward(self): print('%s move forward' %self.nickname) ...... def attack(self,enemy): enemy.life_value-=self.aggressivity class Garen(Hero): pass class Riven(Hero): pass g1=Garen('草叢倫',100,300) r1=Riven('銳雯雯',57,200) print(g1.life_value) #結果:300 r1.attack(g1) print(g1.life_value) #結果:243 ~~~ 提示:用已經有的類建立一個新的類,這樣就重用了已經有的軟件中的一部分設置,大大節省了編程工作量,這就是常說的軟件重用,不僅可以重用自己的類,也可以繼承別人的,比如標準庫,來定制新的數據類型,這樣就是大大縮短了軟件開發周期,對大型軟件開發來說,意義重大. ### 繼承的實現原理 對于定義的每一個類,python會計算出一個方法解析順序(MRO)列表,這個MRO列表就是一個簡單的所有基類的線性順序列表,例如 ~~~ >>> F.mro() #等同于F.__mro__ [<class '__main__.F'>, <class '__main__.D'>, <class '__main__.B'>, <class '__main__.E'>, <class '__main__.C'>, <class '__main__.A'>, <class 'object'>] ~~~ 為了實現繼承,python會在MRO列表上從左到右開始查找基類,直到找到第一個匹配這個屬性的類為止。而這個MRO列表遵循如下準則: 1. 子類會先于父類被檢查 2. 多個父類會根據它們在列表中的順序被檢查 3. 如果對下一個類存在兩個合法的選擇,選擇第一個父類 4. 經典類查找順序遵循深度優先規則 5. 新式類查找順序遵循廣度優先規則 **示范代碼** ~~~python class A(object): def test(self): print('from A') class B(A): def test(self): print('from B') class C(A): def test(self): print('from C') class D(B): def test(self): print('from D') class E(C): def test(self): print('from E') class F(D,E): # def test(self): # print('from F') pass f1=F() f1.test() print(F.__mro__) #只有新式才有這個屬性可以查看線性列表,經典類沒有這個屬性 #結果 from D (<class '__main__.F'>, <class '__main__.D'>, <class '__main__.B'>, <class '__main__.E'>, <class '__main__.C'>, <class '__main__.A'>, <class 'object'>) ~~~ > 新式類繼承順序:F->D->B->E->C->A >經典類繼承順序:F->D->B->A->E->C ## 派生與覆蓋 當然子類也可以添加自己新的屬性或者在自己這里重新定義這些屬性(不會影響到父類),需要注意的是,一旦重新定義了自己的屬性且與父類重名,那么調用新增的屬性時,就以自己為準了,相當于覆蓋了父類的屬性。 ~~~ class Riven(Hero): camp='Noxus' def attack(self,enemy): #在自己這里定義新的attack,不再使用父類的attack,且不會影響父類 print('from riven') def fly(self): #在自己這里定義新的 print('%s is flying' %self.nickname) ~~~ ### 在子類中調用父類的方法 在子類派生出的新方法中,往往需要重用父類的方法,有兩種方式實現 方式一:指名道姓,即父類名.父類方法() ~~~ class Vehicle: #定義交通工具類 Country='China' def __init__(self,name,speed): self.name=name self.speed=speed def run(self): print('開動啦...') class Subway(Vehicle): #地鐵 def __init__(self,name,speed,line): Vehicle.__init__(self,name,speed) self.line=line def run(self): print('地鐵%s號線歡迎您' %self.line) Vehicle.run(self) line13=Subway('中國地鐵','180m/s',13) line13.run() ~~~ 方式二:super()方法 ~~~ class Vehicle: #定義交通工具類 Country='China' def __init__(self,name,speed): self.name=name self.speed=speed def run(self): print('開動啦...') class Subway(Vehicle): #地鐵 def __init__(self,name,speed): #super(Subway,self) 就相當于實例本身 在python3中super()等同于super(Subway,self) super().__init__(name,speed) self.line=line def run(self): print('地鐵%s號線歡迎您' %self.line) super(Subway,self).run() line13=Subway('中國地鐵','180m/s',13) line13.run() ~~~ 兩種方式的區別: 方式一是跟繼承沒有關系的, 方式二的super()是依賴于繼承的,且即使沒有直接繼承關系,super仍然會按照mro繼續往后查找 ~~~ #A沒有繼承B,但是A內super會基于C中的C.mro()繼續往后找 class A: def test(self): print('from A') super().test() class B: def test(self): print('from B') class C(A,B): pass info=C() info.test() print(C.mro()) #打印結果: from A from B [<class '__main__.C'>, <class '__main__.A'>, <class '__main__.B'>, <class 'object'>] ~~~ ## 組合與重用性 軟件重用的重要方式除了繼承之外還有另外一種方式,即:組合 組合指的是,在一個類中以另外一個類的對象作為數據屬性,稱為類的組合 ~~~ class Equip: #武器裝備類 def fire(self): print('release Fire skill') class Riven: #英雄Riven的類, camp='Noxus' def __init__(self,nickname): self.nickname=nickname self.equip=Equip() #用Equip類產生一個裝備,賦值給實例的equip屬性 r1=Riven('銳雯雯') r1.equip.fire() #可以使用組合的類產生的對象所持有的方法 #結果: release Fire skill ~~~ ## 繼承與組合的區別 組合與繼承都是有效地利用已有類的資源的重要方式。但是二者的概念和使用場景皆不同, **1.繼承的方式** 通過繼承建立了派生類與基類之間的關系,它是**一種'是'的關系**,比如白馬是馬,人是動物。 當類之間有很多相同的功能,提取這些共同的功能做成基類,用繼承比較好,比如老師是人,學生是人 **2.組合的方式** 用組合的方式建立了類與組合的類之間的關系,它是**一種'有'的關系**,比如教授有生日,教授教python和linux課程,教授有學生s1、s2、s3... **總結:** 當類之間有顯著不同,并且較小的類是較大的類所需要的組件時,用組合比較好 ### 繼承與組合示例代碼: ~~~ class People: def __init__(self,name,age,sex): self.name=name self.age=age self.sex=sex class Course: def __init__(self,name,period,price): self.name=name self.period=period self.price=price def tell_info(self): print('<%s %s %s>' %(self.name,self.period,self.price)) class Teacher(People): def __init__(self,name,age,sex,job_title): People.__init__(self,name,age,sex) self.job_title=job_title self.course=[] self.students=[] class Student(People): def __init__(self,name,age,sex): People.__init__(self,name,age,sex) self.course=[] # 實例化老師,學生和兩門課程 egon=Teacher('egon',18,'male','金牌講師') s1=Student('牛榴彈',18,'female') python=Course('python','3mons',3000.0) linux=Course('python','3mons',3000.0) #為老師egon和學生s1添加課程 egon.course.append(python) egon.course.append(linux) s1.course.append(python) #為老師egon添加學生s1 egon.students.append(s1) #使用 for obj in egon.course: obj.tell_info() ~~~
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看