一文了解 Python 的 「Magic」 方法

尋夢新聞LINE@每日推播熱門推薦文章,趣聞不漏接❤️

加入LINE好友

一文了解 Python 的 「Magic」 方法 科技 第1張

本文為 AI 研習社編譯的技術博客,原標題 :

Python magic methods or special methods

翻譯 |鄧普斯•傑弗

校對 | 醬番梨 整理 | 菠蘿妹

註:本文的相關鏈接請點擊文末【閱讀原文】進行訪問

在以前的文章中,我聊過了Python的 __getitem__ 和 __setitem__ 方法。這些方法被稱為「魔法」方法、特殊方法或者dunger方法(譯者:國內書籍用「魔法」一詞較多)。那麼,什麼是魔法方法呢?這正是今天我們要說的內容。

P.S.你會再一次的深深的愛上Python語言。

也將是一篇較長的文章,來讓我們開始。

魔法方法究竟是什麼?

魔法方法是一種具有特殊魅力的正常方法。Python通過這些魔法方法可以賦予你的class魔力。這些魔法方法都是以雙下劃線(__)作為前綴和後綴。坦率的講,其實這些方法並沒有什麼魔法,另外這些方法這Python的文檔中也沒有較為詳細的介紹,因此,今天我們就來詳細的看一看這些方法。

魔法方法之初始化

所有的Python開發者都知道,__init__()是一個類(class)的第一個方法,也可以叫做構造函數。雖然,__init__()方法是第一個被創建的,但是它卻不是第一個被調用的執行的,__new__()方法才是最早被調用的方法。

  • __new__()方法:先讀取參數,如:類名稱,args,和kwargs。然後,__new__()方法把這些參數傳遞給對類名稱的__init__()方法。

    語法:__new__(class_name, args, kwargs)

  • __init__()方法:是類的初始化方法或構造方法,這也幾乎用於全局的初始化目的。

    語法:__init__(self, args, kwargs)

  • __del__()方法:類的析構函數。切記,這並不是定義del x,而是定義了一個對象被垃圾回收的行為。

    語法:__del__(self)

看一個例子:

class SimpleInit(object): ''' Class to initialize a list with a value ''' def __init__(self, value=10): self._list = [value] def __del__(self): del self._list

魔法方法之算術運算

算術運算是非常常見的,因此,如果你想創建屬於自己的數據結構,魔法方法會使你的做到更容易。例如:我們可以像這樣,some_list + some_list2,做到Python的列表(list)拼接。類似這種的有趣行為,我們可以通過魔法方法的算術運算做到定義。

  • __add__(self, other)定義加法(+)

  • __sub__(self, other)定義減法 (-)

  • __mul__(self, other)定義乘法 (*)

  • __floordiv__(self, other)定義整除法 (//)

  • __div__(self, other)定義浮點型除法 (/)

  • __mod__(self, other)定義取餘模運算 (%)

  • __and__(self, other)定義按位與(&)

  • __or__(self, other)定義按位或(|)

  • __xor__(self, other)定義按位異或(^)

  • __pow__(self, other)定義指數運算 (**)

  • __lshift__(self, other)定義按位左移 (<<)

  • __rshift__(self, other)定義按位右移(>>)

例如:

class SimpleAdder(object): def __init__(self, elements=[]): self._list = elements def __add__(self, other): return self._list + other._list def __str__(self): return str(self._list) a = SimpleAdder(elements=[1,2,3,4])b = SimpleAdder(elements=[2, 3, 4])print(a + b) # [1, 2, 3, 4, 2, 3, 4]

魔法方法之增量賦值

Python不僅允許我們定義算術運算,也允許我們定義增量賦值運算。如果你不知道什麼是增量賦值是什麼?那麼我們來看一個簡單的例子:

x = 5 x += 1 # This first adds 5 and 1 and then assigns it back to 'x'

因此有的時候,你可能想寫一些自自定義邏輯做到增量賦值操作。魔法方法支持的運算符有:

  • __iadd__(self, other)定義加法 (+=)

  • __isub__(self, other)定義減法 (-=)

  • __imul__(self, other)定義乘法 (*=)

  • __ifloordiv__(self, other)定義整除法 (//=)

  • __idiv__(self, other)定義浮點型除法 (/=)

  • __imod__(self, other)定義取模運算 (%=)

  • __iand__(self, other)定義按位與(&=)

  • __ior__(self, other)定義按位或(|=)

  • __ixor__(self, other)定義按位異或(^=)

  • __ipow__(self, other)定義指數運算 (**=)

  • __ilshift__(self, other)定義按位左移 (<<=)

  • __irshift__(self, other)定義按位右移(>>=)

魔法方法之比較運算

Python有一組廣泛的魔術方法做到比較。我們可以覆蓋默認的比較行為,來定義使用對象的引用方法。下面是比較魔法方法的列表:

  • __eq__(self, other)幫助檢查兩個對象的相等。它定義了相等運算 (==)

  • __ne__(self, other)定義了不等運算(!=)

  • __lt__(self, other)定義了小於運算 (<)

  • __gt__(self, other)定義了大於運算 (>)

  • __le__(self, other)定義了小於等於運算 (<=)

  • __ge__(self, other)定義了大於等於運算 (>=)

例如:

class WordCounter(object): ''' Simple class to count number of words in a sentence ''' def __init__(self, sentence): # split the sentence on ' ' if type(sentence) != str: raise TypeError('The sentence should be of type str and not {}'.format(type(sentence))) self.sentence = sentence.split(' ') self.count = len(self.sentence) def __eq__(self, other_class_name): ''' Check the equality w.r.t length of the list with other class ''' return self.count == other_class_name.count def __lt__(self, other_class_name): ''' Check the less-than w.r.t length of the list with other class ''' return self.count < other_class_name.count def __gt__(self, other_class_name): ''' Check the greater-than w.r.t length of the list with other class ''' return self.count > other_class_name.count word = WordCounter('Omkar Pathak')print(word.count)

魔法方法之類型轉換

很多時候開發人員需要隱性的轉換變量類型,來滿足最要想要的結果。Python是關心你內在數據的類型的一種動態類型語言,除此之外,Python也關心你,哈哈!如果你想要自定義屬於自己的方法,可以借助如下方法:

  • __int__(self)定義類型轉化為 int

  • __long__(self)定義類型轉化為 long

  • __float__(self)定義類型轉化為 float

  • __complex__(self)定義類型轉化為 complex(復數)

  • __oct__(self)定義類型轉化為octal(八進制)

  • __hex__(self)定義類型轉化為 (十六進制)

  • __index__(self)定義類型轉化為一種int, 當對象被用於切片表達式( a slice expression)時

最常用的魔法方法

這里有一些魔法方法你應該經常遇到:

  • __str__(self)定義了str()行為。例如,當你調用print(object_name),無論object_name是什麼都會被__str__()執行

  • __repr__(self)定義了repr()行為。這個很大程度上類似於__str__()。這兩個之間的主要區別是,str()主要是人類可讀的和repr()是機器可讀的

  • __hash__(self)定義了行為調用hash()

  • __len__(self)返回容器的長度

  • __getitem__(self)和__setitem__(self). 更多內容可以詳見我以前的博客文章。

  • __delitem__(self, key)定義了一個刪除一個項目的行為. 例如,del _list[3]

  • __iter__(self)返回一個迭代容器

class CustomList(object): def __init__(self, elements=0): self.my_custom_list = [0] * elements def __str__(self): return str(self.my_custom_list) def __setitem__(self, index, value): self.my_custom_list[index] = value def __getitem__(self, index): return "Hey you are accessing {} element whose value is: {}".format(index, self.my_custom_list[index]) def __iter__(self): return iter(self.my_custom_list)obj = CustomList(12)obj[0] = 1print(obj[0])print(obj)

把這些有魔法的Python禮物送給你,除此之外,還有更多類似的方法,在你需要的時候可以仔細研究。在我研究魔法方法的時候,遇到了一個類似的博客,我強烈建議你去讀一下該文章。

如果有人知道更多的方法請在評論中說明,或者如果你想共享的話,可以直接打開超鏈接。:)

coding 快樂!

想要繼續查看該篇文章相關鏈接和參考文獻?

長按鏈接點擊打開或點擊底部【閱讀原文】:

https://ai.yanxishe.com/page/TextTranslation/933

AI研習社每日更新精彩內容,觀看更多精彩內容:

用Python做到遺傳算法

如何將深度學習應用於無人機圖像的目標檢測

機器學習和深度學習大PK!昆蟲分類誰更強?

Python高級技巧:用一行代碼減少一半內存占用

等你來譯:

五個很厲害的 CNN 架構

如何在神經NLP處理中引用語義結構

特朗普都被玩壞了,用一張照片就能做出惟妙惟肖的 Memoji

讓神經網路說「我不知道」——用Pyro/PyTorch做到貝葉斯神經網路

◆◆敲黑板,劃重點啦!◆◆

AI求職百題斬已經悄咪咪上線啦,點擊下方小程序卡片,開始愉快答題吧!

一文了解 Python 的 「Magic」 方法 科技 第2張

點擊閱讀原文查看本文更多內容

About 尋夢園
尋夢園是台灣最大的聊天室及交友社群網站。 致力於發展能夠讓會員們彼此互動、盡情分享自我的平台。 擁有數百間不同的聊天室 ,讓您隨時隨地都能找到志同道合的好友!