日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程语言 > python >内容正文

python

python 重载的实现(single-dispatch generic function)

發(fā)布時間:2023/12/20 python 63 豆豆
生活随笔 收集整理的這篇文章主要介紹了 python 重载的实现(single-dispatch generic function) 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

DAY 11. python 重載

函數(shù)重載是指允許定義參數(shù)數(shù)量或類型不同的同名函數(shù),程序在運(yùn)行時會根據(jù)所傳遞的參數(shù)類型選擇應(yīng)該調(diào)用的函數(shù)
,但在默認(rèn)情況下,python是不支持函數(shù)重載的,定義同名函數(shù)會發(fā)生覆蓋

def foo(a:int):print(f'int {a}')def foo(b:list):print(f'list{b}')foo(3) foo([i for i in range(3)])# list3 # list[0, 1, 2]

至于不支持的原因,我想大概是沒必要,首先,只在兩種情況下可能發(fā)生函數(shù)重載,一是參數(shù)類型不同,二是參數(shù)個數(shù)不同,對于第一種情況,鴨子類型的存在使得函數(shù)不在乎參數(shù)類型而只關(guān)心參數(shù)的行為,所以你可以傳遞任何類型的參數(shù),對于第二種情況,缺省參數(shù)的使用使得可以傳遞任意多個參數(shù),因此函數(shù)的重載在python中就顯得很雞肋了,但如果非要實現(xiàn)函數(shù)重載,可以使用3.4中增加的轉(zhuǎn)發(fā)機(jī)制即單分派泛型函數(shù)(single-dispatch generic function)來實現(xiàn)重載

11.2 單分派泛型函數(shù)

  • 泛型函數(shù) generic function :由多個函數(shù)組成的函數(shù),可以根據(jù)不同的參數(shù)類型決定調(diào)用那個函數(shù)
  • 單分派,single-dispatch:一種泛型函數(shù)分派形式,其中實現(xiàn)是根據(jù)單個參數(shù)的類型選擇的。

所以,單分派泛型函數(shù)就是根據(jù)函數(shù)的第一個參數(shù)類型決定使用哪個函數(shù)的泛型函數(shù)

將一個函數(shù)聲明為泛型函數(shù)可以使用修飾器@singledispatch,需要從functools模塊導(dǎo)入,singledispatch有兩個常用方法,register和dispatch

from functools import singledispatch@singledispatch def Foo(arg,*args):print(arg)

這樣就實現(xiàn)了一個泛型函數(shù),他的分派發(fā)生在第一個參數(shù)類型上,如果想要基于此實現(xiàn)重載,需要使用他的register方法,

from functools import singledispatch@singledispatch def Foo(arg,*args):print(arg)# 使用了類型注釋 @Foo.register def _1(arg:int,*args):print(f'int - {arg}')# 沒有使用類型注釋,顯式傳遞給修飾器 @Foo.register(list) def _2(arg,*args):print(f'list - {arg}')if __name__ == '__main__':Foo(3) # int - 3Foo([i for i in range(10)]) # list - [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]

對于使用了類型注釋的變量,singledispatch會自動推斷第一個參數(shù)的類型,如上面int的那個,對于沒有使用類型注釋的變量,可以顯式傳遞類型給singledispatch,如下面list的那個

register屬性還可以以函數(shù)的形式調(diào)用,這可以用在lambdas表達(dá)式上,如

>>> def nothing(arg, verbose=False): ... print("Nothing.") ... >>> fun.register(type(None), nothing)

如果沒有實現(xiàn)針對特定類型的注冊,那么就會使用被@singledispatch修飾的函數(shù)

Foo("string") # string

要檢查泛型函數(shù)將為給定類型選擇哪個實現(xiàn),請使用dispatch()屬性

print(Foo.dispatch(int)) # <function _1 at 0x000001D7C2724B70> print(Foo.dispatch(list)) # <function _2 at 0x000001D7C2792E18> print(Foo.dispatch(str)) # <function Foo at 0x000001FB456FC268>

要訪問所有已注冊的實現(xiàn),請使用只讀的registry屬性

11.3 總結(jié)

python默認(rèn)不支持重載,但可以使用單分派泛型函數(shù)實現(xiàn),聲明泛型函數(shù)需要使用修飾器@singledispatch,它有三個屬性,register用來注冊針對特定類型的“重載函數(shù)”,這里必須指明針對的是哪一個特定的類型,可以給第一個參數(shù)類型注釋,也可以給register傳入一個顯式類型,否則會拋出TypeError異常;dispatch屬性用來查看特定的類型將要選擇的函數(shù);registry用來訪問所有已注冊的實現(xiàn)。

參考鏈接:

functools.singledispatch

single dispatch

generic function

python中的重載

為什么 Python 不支持函數(shù)重載?其他函數(shù)大部分都支持的?

總結(jié)

以上是生活随笔為你收集整理的python 重载的实现(single-dispatch generic function)的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。