Öncelikle yapmak istediğim şeyin aptalca kötülükten bir şey olarak kabul edilebileceğini kabul etmeme izin verin, ancak yine de Python'da yapıp yapamayacağımı öğrenmek istiyorum.Bir dekoratör, imzasını değiştirmeden değişkenleri bir işleve nasıl iletebilir?
Diyelim ki, değişkenleri tanımlayan anahtar kelime argümanlarını alan bir işlev dekoratörüm var ve sarılmış işlevdeki bu değişkenlere erişmek istiyorum. Böyle bir şey yapabilir:
def more_vars(**extras):
def wrapper(f):
@wraps(f)
def wrapped(*args, **kwargs):
return f(extras, *args, **kwargs)
return wrapped
return wrapper
Şimdi şöyle bir şey yapabilirsiniz:
@more_vars(a='hello', b='world')
def test(deco_vars, x, y):
print(deco_vars['a'], deco_vars['b'])
print(x, y)
test(1, 2)
# Output:
# hello world
# 1 2
Bu konuda sevmiyorum şey bu dekoratör kullandığınızda, zorunda olmasıdır dekoratöre tokat ek olarak ek değişken ekleyerek, işlevin çağrı imzasını değiştirmek. Eğer fonksiyon için yardım bakarsak Ayrıca, size işlevini çağırarak kullanılacak beklenen değiliz fazladan değişken bakın:
Bu kullanıcı işlevi çağırmak için beklenen gibi görünmesini sağlarhelp(test)
# Output:
# Help on function test in module __main__:
#
# test(deco_vars, x, y)
3 parametresi ile, ama açıkçası bu işe yaramaz. Bu nedenle, ilk parametrenin arayüzün bir parçası olmadığını belirten bir mesaj eklemeniz gerekecek, sadece bir uygulama detayı ve göz ardı edilmemelidir. Gerçi bu berbat bir şey. Bu değişkenleri küresel ölçekte bir şeye asmadan bunu yapmanın bir yolu var mı? İdeal olarak, ben aşağıdaki gibi bakmak istiyorum:
@more_vars(a='hello', b='world')
def test(x, y):
print(a, b)
print(x, y)
test(1, 2)
# Output:
# hello world
# 1 2
help(test)
# Output:
# Help on function test in module __main__:
#
# test(x, y)
Bir Python 3 Varsa tek çözüm ile memnunum.
Belki de ihtiyacınızı daha çok tanımlamalısınız. İşlevi süslemek için sadece bir şans elde edersiniz, bu yüzden sadece a = 'merhaba' 'dekoratöre koymanın avantajı, sadece işlevin ilk satırı olarak değil, yerine koymak? –
"Test" kelimesinin herhangi bir şekilde tanımlanmasına gerek kalmadan, daha önce derlendikten sonra "testin" kapanmasına "extras" ın nasıl enjekte edileceğini soruyorsunuz gibi geliyor. Eğer öyleyse, bazı korkunç hackler olmadan mümkün olacağını düşünmüyorum. – abarnert
Ama bir dekoratör yerine bir [MacroPy] (https://github.com/lihaoyi/macropy) makrosu kullanarak, bunun kolay olacağını tahmin ediyorum… Bu kabul edilebilir bir cevap olur mu? – abarnert