Комментарии (1)
Ответ сгенерирован нейросетью и может содержать ошибки
Декораторы и элементы в Python
Декоратор — это функция или класс, которые модифицируют поведение другой функции или класса. Вопрос о "закидывании элементов в декоратор" может интерпретироваться несколькими способами.
Что такое декоратор
Декоратор — это паттерн проектирования, который позволяет динамически добавлять новую функциональность к существующим объектам. В Python это реализуется через функции высшего порядка или классы, которые оборачивают исходную функцию.
Передача аргументов в декоратор
Да, в декоратор можно передавать аргументы (элементы). Это делается через создание фабрики декораторов — функции, которая возвращает сам декоратор:
def repeat(times):
def decorator(func):
def wrapper(*args, **kwargs):
for _ in range(times):
result = func(*args, **kwargs)
return result
return wrapper
return decorator
@repeat(times=3)
def greet(name):
print(f"Привет, {name}!")
return name
Декоратор с несколькими аргументами
Можно передавать сложные структуры данных:
def validate_types(**type_map):
def decorator(func):
def wrapper(*args, **kwargs):
for param, expected_type in type_map.items():
if param in kwargs:
if not isinstance(kwargs[param], expected_type):
raise TypeError(f"{param} должен быть {expected_type}")
return func(*args, **kwargs)
return wrapper
return decorator
@validate_types(age=int, name=str)
def create_user(name, age):
return {"name": name, "age": age}
Класс-декоратор со списком элементов
Можно использовать класс как декоратор:
class LogCallsWith:
def __init__(self, handlers):
self.handlers = handlers
def __call__(self, func):
def wrapper(*args, **kwargs):
for handler in self.handlers:
handler(f"Вызов {func.__name__}")
return func(*args, **kwargs)
return wrapper
def log_handler(msg):
print(f"[LOG] {msg}")
@LogCallsWith([log_handler])
def process_data(data):
return f"Обработано: {data}"
Практическое применение в Data Engineering
Декораторы используются для логирования, переповторов при ошибках, валидации входных данных и мониторинга производительности:
import functools
import time
def retry_on_fail(max_attempts=3, delay=1):
def decorator(func):
@functools.wraps(func)
def wrapper(*args, **kwargs):
for attempt in range(max_attempts):
try:
return func(*args, **kwargs)
except Exception as e:
if attempt == max_attempts - 1:
raise
time.sleep(delay)
return None
return wrapper
return decorator
@retry_on_fail(max_attempts=3, delay=2)
def fetch_data_from_api(url):
return requests.get(url).json()
Вывод
Декораторы — очень гибкий инструмент. Да, можно передавать в них элементы (аргументы), структуры данных, функции. Это делает код более модульным и переиспользуемым.