2012-02-29 51 views
3

有什麼辦法可以獲得應用到函數的裝飾器列表,而不訴諸像修飾裝飾器之類的黑客行爲?我可以得到應用於函數的裝飾器列表嗎?

+0

我已經在這裏大多-回答了這個問題,在一個稍微不同的(但很容易適應)形式:http://stackoverflow.com/questions/5910703/howto-get-all-methods-of-a-python -class-with-given-decorator裝飾裝飾器比源代碼黑客,C-python黑客等裝飾裝飾品要少得多。我認爲「裝飾裝飾器」根本不算黑客,而且是一種常用技術。(也有人可能會認爲這個問題是鏈接問題的一個子集,因爲方法主要是函數,但允許應用更多種技巧。) – ninjagecko 2012-02-29 04:33:39

回答

3

不是。首先,因爲並不是所有的裝飾器都返回一個包裝函數;裝飾器可以簡單地修改現有的函數(也許在其上設置一個屬性) - Python不會記錄每個屬性觸及哪個函數,顯然。其次,儘管您可能會向垃圾收集器詢問包含裝飾函數的引用的閉包以及具有該閉包的函數,但並非每個在閉包中引用另一個函數的函數都是由裝飾器應用的包裝器。然後是裝飾者需要爭論的問題;在實際裝飾功能之前,還有一層額外的內部功能。最後,並非所有裝飾器都是函數,並非所有裝飾對象都是函數。

總之,你也許能接近它一些時間,但即使它的作品,這將是一個巨大的黑客,僅適用於CPython的。沒有任何簡單的,有文件記錄的方式來做到這一點。

+0

+ +1因爲想出更多想象力的駭人聽聞比我能。結果是即使是一個半功能的解決方案也會比「裝飾裝飾者」更加駭人聽聞。再見,這其實並不是那麼猖獗。 – senderle 2012-02-29 04:33:55

1

我相信這是不可能的,因爲裝飾者可以選擇替換函數,包裝函數,返回他們想要的任何東西。它不是那麼「適用」到功能上。

3

我很不安張貼這樣的一個答案,因爲事情似乎總是泡漲了Python標準庫的深處證明我是錯的。但我很肯定答案是否定的。

問題是裝飾者本身就是功能 - 整個@foo的東西只是func = foo(func)的語法糖 - 所以它們不會給你任何額外的功能,但這些功能還沒有給你。這不是很多。

這是可能的,你也許能等閒逛在func_dictfunc_globalsfunc_defaultsfunc_closure和,並進行一些猜測,但它不太可能有不涉及手工編碼的行爲變成一個好的解決方法裝飾者。或者,正如你所說,裝飾裝飾者。

0

至於其他的答案說了,裝修不能換的功能,只是修改它 - 在這種情況下,ytou將無法找到他們。

對於包裝裝飾器,儘管你可以求助於使用Python的調試鉤子 - 它不會很容易,也不會是「乾淨的」 - 但它可以做到:你可以選擇一個調試鉤子來調用每個鉤子當你輸入一個函數,並調用你的裝飾函數 - 每次你的鉤子被調用時,你已經進入一個新的函數 - 使用自省,看看這是否是你的「最終」功能(如果你的裝飾器不使用functools .wrap自己,你想要的功能是保持原有__name__屬性只有一個,否則麻煩) - 見 sys.settracebdb模塊上的文件和檢查,如果你拿出的東西。

但是當你想到這一點,裝飾裝修母鹿不看那個hackish的了,不是嗎?

相關問題