簡體   English   中英

如何將自我傳遞給裝飾方法?

[英]How to pass self into a decorated method?

我正在嘗試使用裝飾器將隱私修改器實現到 python 中。 我的問題是,每當我裝飾一個以 self 作為參數的方法時,當使用點表示法調用該方法時,它不會自動傳遞 self 。

公共裝潢師class:

class Public:
    def __init__(self, method, *args):
        if type(method).__name__ == 'function':
            self.method = method

    def __call__(self, *args, **kwargs):
        return self.method(*args, **kwargs)

示例代碼:

class Test:
    @Public
    def test(self):
        return "Hello"


class Test1(Test):
    def __init__(self):
        super().__init__()
        print(self.test())


x = Test1()

我如何將自己傳遞給Public.__call__

我嘗試定期傳遞自我:

class Test:
    @Public
    def test(self):
        return "Hello"


class Test1(Test):
    def __init__(self):
        super().__init__()
        print(self.test(self))


x = Test1()

這行得通,但我寧願不必在每次需要調用方法時都這樣做。

我找到了答案

下面是如果其他人正在做類似的事情:

首先,我必須創建一個裝飾器 function,它更改了class中的 getattribute function

def modifiable(cls):
    if isinstance(cls, type):
        original_getattr = cls.__getattribute__

        def getattr(_self, name):
            attr = original_getattr(_self, name)

            if isinstance(attr, Modifier):

                def wrapper(*args, **kwargs):
                    return attr(_self, *args, **kwargs)

                return wrapper

            return attr

        cls.__getattribute__ = getattr

    return cls

我還創建了一個空的Modifier class,所有隱私修飾符都繼承自該修飾符,以便更輕松地檢查方法是否被修改。

示例代碼:

@modifiable
class Test:
    @Protected
    def test(self):
        return "Hello"


@modifiable
class Test1(Test):
    x = 1

    def __init__(self):
        super().__init__()
        print(self.test())

test = Test1()
print(test.test())

和 output:

Hello
Traceback (most recent call last):
  File "C:\Users\tyson\OneDrive\Documents\GitHub\better-decorators\src\test.py", line 21, in <module>
    print(test.test())
privacy.AccessError: test is a protected method

(privacy.AccessError 是自定義錯誤)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM