成人免费xxxxx在线视频软件_久久精品久久久_亚洲国产精品久久久_天天色天天色_亚洲人成一区_欧美一级欧美三级在线观看

Python中的高階概念屬性:五個你應該搞明白的知識點

開發 后端
在現代編程世界中,面向對象編程(OOP)語言在改變軟件開發中的設計和實現模式方面發揮了進化作用。作為OOP家族的重要成員,Python在過去10年左右逐漸流行起來。與其他OOP語言一樣,Python圍繞大量不同的對象操作其數據,包括模塊、類和函數。

 前言

在現代編程世界中,面向對象編程(OOP)語言在改變軟件開發中的設計和實現模式方面發揮了進化作用。作為OOP家族的重要成員,Python在過去10年左右逐漸流行起來。與其他OOP語言一樣,Python圍繞大量不同的對象操作其數據,包括模塊、類和函數。

[[343499]]

如果您有任何OOP語言的編程經驗,您應該知道所有對象都有其內部特征數據,稱為字段、屬性或屬性。在Python中,這些對象綁定的特征數據通常稱為屬性。在本文中,我將特別在自定義類的上下文中討論它們

1.類屬性

為了更好地管理項目中的數據,我們經常需要創建自定義類。在Python中,類也是對象,這意味著它們可以有自己的屬性。讓我們看一個例子。

  1. >>> class Dog: 
  2. ...     genus = "Canis" 
  3. ...     family = "Canidae" 
  4. ...>>> Dog.genus'Canis' 
  5. >>> Dog.family'Canidae' 
  6. >>> dir(Dog)['__class__''__delattr__''__dict__''__dir__''__doc__''__eq__''__format__',  
  7.  '__ge__''__getattribute__''__gt__''__hash__''__init__''__init_subclass__',  
  8.  '__le__''__lt__''__module__''__ne__''__new__''__reduce__''__reduce_ex__',  
  9.  '__repr__''__setattr__''__sizeof__''__str__''__subclasshook__''__weakref__',  
  10.  'family''genus'

如上所示,我們聲明了一個名為Dog的類。因為所有的狗都屬于犬類屬和犬科家族,所以我們創建了兩個類屬性,分別命名為屬和科來存儲這兩條信息。如您所見,我們可以直接使用類來訪問這些屬性。我們可以使用函數dir來顯示狗的屬性列表,其中包括家族和屬。

這些定義為類級別的屬性稱為類屬性,類可以直接檢索它們。但是,與其他OOP語言不同,Python中的實例對象也可以直接訪問這些類屬性,如下面的代碼片段所示。

  1. >>> Dog().genus 
  2. 'Canis' 
  3. '>>> Dog().family 
  4. 'Canidae' 

2.實例屬性

通過自定義類,我們還可以為實例對象設置屬性。這些屬性稱為實例屬性,這意味著它們是特定于實例的數據。讓我們繼續狗類。

  1. >>> class Dog: 
  2. ...     genus = "Canis" 
  3. ...     family = "Canidae" 
  4. ......     def __init__(self, breed, name): 
  5. ...         self.breed = breed...         self.name = name... 

在上面的代碼中,我們定義了__init__函數,它將作為創建一個新的Dog實例的構造方法。第一個參數self引用了我們正在創建的實例。在實例化期間(即創建新實例),我們將為新實例對象分配品種和名稱信息,這些屬性將成為實例特征的一部分,如下所示。

  1. >>> dog = Dog("Rottweiler""Ada"
  2. >>> dog.name'Ada' 
  3. >>> dog.breed'Rottweiler' 

需要注意的一點是,我們可以為具有與class屬性相同的屬性的實例賦值。在這種情況下,當您檢索實例的這個屬性時,將不會檢索class屬性。換句話說,當您使用一個實例對象來檢索class屬性時,Python將首先檢查實例本身是否有一個用相同名稱設置的屬性。如果沒有,Python將使用class屬性作為回退。此外,設置一個實例的屬性不會影響同名類的屬性。讓我們在下面的代碼片段中看看這些特征。

  1. >>> dog.genus = "Felis" 
  2. >>> dog.genus'Felis' 
  3. >>> Dog('Poodle''Cutie').genus 
  4. 'Canis' 

3.函數作為屬性

在Python中,一切都是對象,前面我已經提到類是對象。此外,函數是Python對象。在類中,我們可以定義函數,通常稱為方法。根據使用這些函數的方式,我們可以將它們進一步分類為類方法、靜態方法和實例方法。在這里,理解這些差異并不是必須的。

盡管某些OOP語言將屬性(或屬性)和函數視為不同的實體,但Python將這些方法(函數)視為類的屬性——與我們前面定義的類屬性沒有太大區別。讓我們用上面提到的三種方法來更新Dog類:類方法、靜態方法和實例方法,如下所示。

  1. >>> class Dog: 
  2. ...     genus = "Canis" 
  3. ...     family = "Canidae" 
  4. ......     def __init__(self, breed, name): 
  5. ...         self.breed = breed...         self.name = name......     @classmethod...     def from_tag(cls, tag_info): 
  6. ...         breed = tag_info["breed"
  7. ...         name = tag_info["name"
  8. ...         return cls(breed, name
  9. ......     @staticmethod...     def can_bark(): 
  10. ...         print("Yes. All dogs can bark."
  11. ......     def bark(self): 
  12. ...         print("The dog is barking."
  13. ...  

對于更新后的類,我們可以使用函數dir檢查類的屬性列表。如下所示,類方法和靜態方法都包含在列表中。

  1. >>> dir(Dog) 
  2. ['__class__''__delattr__''__dict__''__dir__''__doc__''__eq__''__format__',  
  3. '__ge__''__getattribute__''__gt__''__hash__''__init__''__init_subclass__',  
  4. '__le__''__lt__''__module__''__ne__''__new__''__reduce__''__reduce_ex__',  
  5. '__repr__''__setattr__''__sizeof__''__str__''__subclasshook__''__weakref__',  
  6. 'bark''can_bark''family''from_tag''genus'

然而,有一件事可能會讓一些人感到驚訝,那就是該列表中包含了實例方法bark。我們知道,實例方法是那些由實例對象調用的函數,因此有些人可能認為這些實例方法應該綁定到所有單獨的實例。然而,在Python中卻不是這樣。在解釋實例方法如何工作之前,讓我們先看看下面的代碼。

  1. >>> dog = Dog("Rottweiler""Ada"
  2. >>> dog.bark()The dog is barking. 
  3. >>> Dog.bark(dog)The dog is barking. 

如上所示,我們首先創建了Dog類的一個實例。與其他OOP語言一樣,實例對象可以直接調用實例方法bark。然而,Python與其他語言的不同之處在于,實例方法的調用是通過類來操作的,通過傳遞實例作為參數來調用定義的函數(即,dog .bark(dog))。換句話說,instance.inst_method()在本質上與Python中的Class.inst_method(instance)相同。

之所以可以這樣做,是因為Dog類“擁有”實例方法,這是一種節省內存的機制,因為Python不需要為每個實例對象創建單獨的函數副本。相反,當一個實例調用一個實例方法時,Python將調用委托給類,該類將通過傳遞實例調用相應的函數(它將被設置為已定義函數中的self參數)。

4.私有屬性

如果您有OOP的經驗,就不應該不熟悉訪問修飾符的存在,比如public、private和protected。這些修飾符限制了可以訪問修改的屬性和函數的范圍。然而,您很少在Python中聽到這樣的討論。實際上,如果借用OOP中的術語,所有Python屬性都是公共的。如上所示,在類和實例可以訪問的地方,類和實例屬性都可以自由訪問。因此,嚴格地說,Python中沒有真正的私有或受保護的屬性(后面將討論)。我們只是類比地使用這些術語,以便來自其他OOP背景的程序員更容易理解相關的編碼約定(是的,只是一種約定,沒有作為真正的訪問控制加以加強)。

讓我們首先討論一下如何在Python中定義“私有”屬性。慣例是用兩個前導下劃線命名這些屬性,并且不超過一個后引下劃線。考慮下面更新過的Dog類的示例—為了簡單起見,我們省略了前面定義的其他屬性。

  1. >>> class Dog: 
  2. ...     def __init__(self, breed, name): 
  3. ...         self.breed = breed...         self.name = name...         self.__tag = f"{name} | {breed}" 
  4. ... >>> dog = Dog("Rottweiler""Ada"
  5. >>> dog.name'Ada' 
  6. >>> dog.__tagTraceback (most recent call last):  File "<stdin>", line 1, in <module> 
  7. AttributeError: 'Dog' object has no attribute '__tag' 

在上面的更新之后,Dog實例將擁有一個名為tag的私有屬性,正如其名稱所示。實例對象仍然可以像以前一樣訪問它的其他屬性(例如,名稱)。然而,實例不能訪問私有屬性剩余的標記,這可能是我們所期望的。實際上,這種對訪問這些屬性的限制正是它們被稱為“私有”屬性的原因。但它是怎么發生的,在引擎蓋下?畢竟,我前面提到過,所有Python屬性在默認情況下都是公共的。下面將向您展示Python如何實現“私有”屬性。

  1. >>> dog.__dict__ 
  2. {'breed''Rottweiler''name''Ada''_Dog__tag''Ada | Rottweiler'
  3. >>> dog._Dog__tag'Ada | Rottweiler' 

__dict__特殊方法(也稱為dunder方法,在名稱前后都有雙下劃線)能夠顯示對象的字典表示。具體來說,字典中的鍵-值對是對象的屬性及其值。正如我們所看到的,除了bread和name屬性之外,還有一個名為_dog__tag標記的屬性。這個屬性正是私有屬性__tag通過一個稱為mangling的過程與對象關聯的方式。

具體來說,mangling或name mangling是使用_ClassName作為私有屬性的前綴,這樣我們就人為地創建了對這些“私有”屬性的訪問限制。但是,如果我們確實想檢索任何私有屬性,我們仍然可以使用被破壞的名稱訪問它,就像我們在代碼片段中使用_dog__標記所做的那樣。

5.受保護的屬性

在上一節中,我們討論了私有屬性,但是受保護的屬性呢?Python中與受保護屬性對應的屬性名稱只有一個下劃線。不像雙下劃線會導致混亂,單下劃線前綴不會改變Python解釋器處理這些屬性的方式——它只是Python編程世界的一個慣例,表示他們(例如,編碼器)不希望你訪問這些屬性。但是,如果你堅持要訪問它們,你仍然可以這樣做。讓我們看看下面的代碼。

  1. >>> class Dog: 
  2. ...     def __init__(self, breed, name): 
  3. ...         self.breed = breed...         self.name = name...         self.__tag = f"{name} | {breed}" 
  4. ...         self._nickname = name[0] 

我們通過創建一個名為_nickname的實例屬性來更新類Dog。正如其名稱使用下劃線前綴所表明的那樣,按照約定,它被認為是一個“受保護”的屬性。我們仍然可以將這些受保護的屬性作為其他“公共”屬性來訪問,但是一些ide或Python編輯器不會為這些非公共屬性提供提示(例如,自動完成提示)。有關這些使用Jupyter筆記本的例子,請參見屏幕截圖。

Python中的高階概念屬性:五個你應該搞明白的知識點

如果我們使用模塊而不是類,就像我們在這里所做的那樣,當我們使用from _module import *導入模塊時,帶有下劃線前綴的名稱將不會被導入,從而提供了一種機制來限制對這些“受保護的”屬性的訪問。

 

責任編輯:華軒 來源: Huangwei AI
相關推薦

2020-09-23 13:45:07

Python編程語言

2021-01-15 08:35:49

Zookeeper

2022-10-27 21:01:03

JavaScrip面試題開發

2015-06-09 14:57:27

HTML5知識點

2023-01-10 09:24:47

Python編程語言

2022-02-09 16:25:34

區塊鏈技術加密貨幣

2024-09-19 16:00:01

網絡編程網絡Python

2021-08-09 14:47:34

Go語言開發

2019-11-25 21:46:12

數據湖云計算數據倉庫

2020-09-25 16:52:57

Python

2023-12-22 15:32:20

2021-04-19 08:35:44

PythonPython語言Python基礎

2009-08-02 21:47:35

安防線纜

2022-08-01 07:42:17

線程安全場景

2013-01-18 08:53:27

Android開發學習Android

2016-07-22 15:22:52

2021-11-07 14:34:26

跨域網絡后端

2011-07-10 15:18:11

開發

2023-12-19 16:39:18

CSS開發前端

2012-04-23 15:49:04

點贊
收藏

51CTO技術棧公眾號

主站蜘蛛池模板: 国产精久久久久久 | 免费在线观看黄色av | 国产精品久久久久久久久免费樱桃 | www.v888av.com | 九九热九九| 亚洲精品资源 | www.色五月.com| 久久黄网 | 精精国产xxxx视频在线播放7 | 91成人精品 | 精品国产不卡一区二区三区 | 激情免费视频 | 99九色| 欧美456| 成人免费视频观看视频 | 2019天天干天天操 | 精品国产欧美一区二区三区不卡 | 性国产丰满麻豆videosex | 精品国产一区二区久久 | 日韩中文字幕在线播放 | 妞干网福利视频 | 99精品99久久久久久宅男 | 国产精品高潮呻吟久久av黑人 | 亚洲国产中文字幕 | 欧美一级在线观看 | 台湾a级理论片在线观看 | 免费一级欧美在线观看视频 | 免费看日韩视频 | 国产综合久久久久久鬼色 | 91精品无人区卡一卡二卡三 | 精品国产黄a∨片高清在线 www.一级片 国产欧美日韩综合精品一区二区 | 精品国产乱码一区二区三 | 亚洲精品国产一区 | 日日操操操 | 毛片com | 亚洲三级av | 欧美日韩一区在线观看 | 久久亚洲一区 | 久久毛片 | 久久久99精品免费观看 | 国产成人精品综合 |