Python'da bir kapanış, kendisine sabit bir şekilde bağlı değişkenlere sahip bir işlev örneğidir.
Aslında, veri modeli bunu işlevlerin __closure__
özniteliğinin açıklamasında açıklar :
Hiçbiri veya işlevin serbest değişkenleri için bağlar içeren bir hücre kümesi . Sadece oku
Bunu göstermek için:
def enclosure(foo):
def closure(bar):
print(foo, bar)
return closure
closure_instance = enclosure('foo')
Açıkça, artık değişken adından işaret ettiğimiz bir işleve sahip olduğumuzu biliyoruz closure_instance
. Görünüşe göre, eğer onu bir nesneyle çağırırsak bar
, dizeyi 'foo'
ve dizgi temsili ne olursa olsun yazdırmalıdır .bar
.
Aslında, dize 'foo' olan fonksiyonun örneğine bağlı ve doğrudan erişerek, buradan okuyabilirsiniz cell_contents
ait başlığın ilk (ve tek) hücrenin niteliğini __closure__
özniteliği:
>>> closure_instance.__closure__[0].cell_contents
'foo'
Bir kenara, hücre nesneleri C API belgelerinde açıklanmıştır:
"Hücre" nesneleri, birden çok kapsam tarafından referans verilen değişkenleri uygulamak için kullanılır
Kapanışımızın kullanımını gösterebiliriz 'foo'
, bunun işlevde takılı kaldığını ve değişmediğini belirterek :
>>> closure_instance('bar')
foo bar
>>> closure_instance('baz')
foo baz
>>> closure_instance('quux')
foo quux
Ve onu hiçbir şey değiştiremez:
>>> closure_instance.__closure__ = None
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: readonly attribute
Kısmi İşlevler
Verilen örnek, kapanışı kısmi bir işlev olarak kullanır, ancak tek amacımız buysa, aynı hedefe şu şekilde de ulaşılabilir: functools.partial
>>> from __future__ import print_function
>>> partial_function = functools.partial(print, 'foo')
>>> partial_function('bar')
foo bar
>>> partial_function('baz')
foo baz
>>> partial_function('quux')
foo quux
Kısmi fonksiyon örneğine uymayan daha karmaşık kapanışlar da var ve bunları zaman elverdikçe daha fazla göstereceğim.
nonlocal
piton 3'te eklenmiş, piton 2.x yoktu tam üzerinde, okuma-yazma kapamaları (yani değişkenler üzerinde kapalı, ama onların değerlerini değiştirmez okumak olabilir)