Python'da Dekoratörler Nasıl Oluşturulur ve Kullanılır

Python'da dekoratörlerin nasıl yazılacağını ve uygulanacağını öğrenin. Sarma işlevlerinde, davranışı değiştirmede, bağımsız değişkenleri yönetmede ve sarmalarla meta verileri korumada uzmanlaşın.

Bu Çözümü Editör'de deneyin

Genel Bakış

Dekoratörler Python'un en zarif ve güçlü sözdizimi özelliklerinden biridir ve bir işlevin veya sınıfın davranışını, kodunu kalıcı olarak değiştirmeden değiştirmenize olanak tanır. Yürütme sürelerinin günlüğe kaydedilmesi, kullanıcı kimlik doğrulamasının zorunlu kılınması, sonuçların önbelleğe alınması (notlandırma) ve API uç noktalarının denetlenmesi gibi kesişen konular için yaygın olarak kullanılırlar.

Temelde dekoratör, başka bir işlevi argüman olarak alan, bazı özel mantıklar enjekte eden iç içe geçmiş bir sarmalayıcı işlevi tanımlayan ve bu sarmalayıcı işlevi döndüren daha yüksek düzeyde bir işlevdir. Python, işlevlere dekoratörler uygulamak için `@' sembolünü kullanarak temiz bir kısa sözdizimi sağlayarak onları görsel olarak şık hale getirir.

Dekoratörler yazarken, genellikle dekore edilmiş fonksiyonun herhangi bir sayıda konumsal ve anahtar kelime argümanını desteklemesini isteyeceksiniz. Bunu, iç içe sarıcı işlevini "*args" ve "**kwargs" kabul edecek ve bunları hedef işleve iletecek şekilde tasarlayarak başarabilirsiniz. Ek olarak, orijinal işlevin belge dizesini ve ad meta verilerini korumak için sarmalayıcı işlevinde "functools.wraps" komutunu kullanmalısınız.

Kod ve Yürütme Çıkışı

Bu komut dosyası, bir günlük dekoratörü yazmayı ve girişleri, çıkışları ve meta verileri denetlemek için bir işlevi sarmalamayı gösterir.

decorators_tutorial.py
Editör'de deneyin
from functools import wraps

# 1. Defining a decorator
def log_execution(func):
    @wraps(func) # Preserves original function metadata
    def wrapper(*args, **kwargs):
        print(f"[Log] Calling function: {func.__name__} with args: {args}")
        result = func(*args, **kwargs)
        print(f"[Log] Finished {func.__name__}. Result: {result}")
        return result
    return wrapper

# 2. Applying the decorator using @ syntax
@log_execution
def add_numbers(a, b):
    """Adds two numbers and returns the sum."""
    return a + b

# 3. Invoking the decorated function
sum_result = add_numbers(15, 25)
print("Sum Result:", sum_result)

# Verifying metadata preservation
print("Docstring preserved:", add_numbers.__doc__)
Terminal Çıkışı
[Log] Calling function: add_numbers with args: (15, 25)
[Log] Finished add_numbers. Result: 40
Sum Result: 40
Docstring preserved: Adds two numbers and returns the sum.

Adım Adım Uygulama

  • Hedef işlevi argüman olarak alan bir dış dekoratör işlevi tanımlayın.
  • Orijinal meta verileri korumak için iç içe sarmalayıcı işlevinize @functools.wraps(func) öğesini içe aktarın ve uygulayın.
  • Giriş değişkenlerini yakalamak, mantığı enjekte etmek ve hedef işlevi çağırmak için sarmalayıcı(*args, **kwargs) uygulayın.
  • Sarmalayıcı işlev nesnesini dekoratör başlık bloğundan döndürün.
  • @decorator_name kullanarak dekoratörü doğrudan hedef fonksiyon imzasının üzerine uygulayın.

Sıkça Sorulan Sorular

Dekoratörlerin içinde @functools.wraps neden gerekli?

Sarma olmadan, dekore edilen işlev orijinal kimliğini kaybeder (__name__ ve __doc__ niteliklerinin yerini iç içe sarmalayıcı işlevinkiler alır), bu da hata ayıklamayı ve kodun iç gözlemini zorlaştırır.

Tek bir işleve birden fazla dekoratör uygulayabilir miyim?

Evet! Birden fazla @ satırını yığın halinde yerleştirerek dekoratörleri zincirleyebilirsiniz. Python bunları aşağıdan yukarıya doğru uygular (işlev tanımına en yakın olanı ilk önce çalıştırılır).

İlgili Konular

Önerilen Python Kaynakları

İlgili etkileşimli eğitimler, yardımcı sayfalar ve kod karşılaştırmalarıyla bilginizi genişletin.