Python Decorator Basics
知っておくべきことは...
デコレーション
簡単に言えば、Pythonレコーダは、ある関数(wrap)を囲むことによって関数の動作を変更する関数であり、PythonはSyntatic Sugarを追加することによってレコーダをターゲット関数により容易に適用する.def my_decorator(func):
def my_wrapper():
# Wrapper는 데코레이터가 받은 함수의 행동 또는 인자를 수정한다.
# 이 경우 원 함수를 두 번 실행한다.
func()
func()
# 데코레이터는 Wrapper를 리턴한다.
return my_wrapper
# 데코레이터가 적용된 함수는 사실 my_wrapper(say_hello)와 같다.
@my_decorator
def say_hello():
print("Hello?")
>> say_hello() # 이 실행은 사실 my_wrapper(say_hello)()와 같다.
"Hello?"
"Hello?"
円関数に入力パラメータが含まれている場合:
ソース関数に入力パラメータがある場合は、データレコーダのラッパ関数を同じパラメータを受け入れるように設定する必要があります.
ただし、この場合、制限デコーダのターゲット関数は、同じ数のパラメータを受け入れる関数のみを修正することができる.
解決策は、包装関数に*args
、**kwargs
パラメータを適用することである.def my_decorator(func):
def my_wrapper(*args, **kwargs):
# wrapper가 받은 임의의 인자를 그대로 원 함수에 전달한다.
func(*args, **kwargs)
func(*args, **kwargs)
return my_wrapper
@my_decorator
def say_hello():
print("Hello?")
@my_decorator
def say_name(name):
print(f"Hello {name}?")
>> say_hello()
"Hello?"
"Hello?"
>> say_name("Jun")
"Hello Jun?"
"Hello Jun?"
円関数の戻り値を返します
簡単に言えば、包装器は必要な関数を実行し、結果を一緒に返すことができる.def my_decorator(func):
def my_wrapper(*args, **kwargs):
# wrapper가 받은 임의의 인자를 그대로 원 함수에 전달한다.
func(*args, **kwargs)
return func(*args, **kwargs)
return my_wrapper
元の関数のメタデータ情報を保持
関数がレコーダによってカプセル化されると、関数のメタデータ情報は関数を指さなくなります.
この場合、functool
バージョンライブラリで定義されたdecorator @functool.wraps
を使用して、decorator定義でパッケージを装飾します.
たとえば、def my_decorator(func):
def my_wrapper(*args, **kwargs):
func(*args, **kwargs)
func(*args, **kwargs)
return my_wrapper
import functools
def better_decorator(func):
@functools.wraps(func)
def my_wrapper(*args, **kwargs):
func(*args, **kwargs)
func(*args, **kwargs)
return my_wrapper
@my_decorator
def say_name(name):
print(f"Hello {name}?")
@my_decorator2
def say_name2(name):
print(f"Hello {name}?")
>> say_name.__name__
'my_wrapper'
>> say_name2.__name__
'say_name2'
Reference
def my_decorator(func):
def my_wrapper():
# Wrapper는 데코레이터가 받은 함수의 행동 또는 인자를 수정한다.
# 이 경우 원 함수를 두 번 실행한다.
func()
func()
# 데코레이터는 Wrapper를 리턴한다.
return my_wrapper
# 데코레이터가 적용된 함수는 사실 my_wrapper(say_hello)와 같다.
@my_decorator
def say_hello():
print("Hello?")
>> say_hello() # 이 실행은 사실 my_wrapper(say_hello)()와 같다.
"Hello?"
"Hello?"
def my_decorator(func):
def my_wrapper(*args, **kwargs):
# wrapper가 받은 임의의 인자를 그대로 원 함수에 전달한다.
func(*args, **kwargs)
func(*args, **kwargs)
return my_wrapper
@my_decorator
def say_hello():
print("Hello?")
@my_decorator
def say_name(name):
print(f"Hello {name}?")
>> say_hello()
"Hello?"
"Hello?"
>> say_name("Jun")
"Hello Jun?"
"Hello Jun?"
def my_decorator(func):
def my_wrapper(*args, **kwargs):
# wrapper가 받은 임의의 인자를 그대로 원 함수에 전달한다.
func(*args, **kwargs)
return func(*args, **kwargs)
return my_wrapper
def my_decorator(func):
def my_wrapper(*args, **kwargs):
func(*args, **kwargs)
func(*args, **kwargs)
return my_wrapper
import functools
def better_decorator(func):
@functools.wraps(func)
def my_wrapper(*args, **kwargs):
func(*args, **kwargs)
func(*args, **kwargs)
return my_wrapper
@my_decorator
def say_name(name):
print(f"Hello {name}?")
@my_decorator2
def say_name2(name):
print(f"Hello {name}?")
>> say_name.__name__
'my_wrapper'
>> say_name2.__name__
'say_name2'
Reference
この問題について(Python Decorator Basics), 我々は、より多くの情報をここで見つけました https://velog.io/@junsikchoi/Python-Decorator-Basicsテキストは自由に共有またはコピーできます。ただし、このドキュメントのURLは参考URLとして残しておいてください。
Collection and Share based on the CC Protocol