Closures - Kapatmalar - 4


Bir fonksiyon ya da metot () -> T türünden bir fonksiyon parametresine sahipse onu hiç küme parantezleri olmadan çağırabiliriz. Bunun için parametre değişkeninin @autoclosure özniteliği ile niteliklendirilmesi gerekir.
Örneğin:
func foo(@autoclosure f: () -> Int){
print(f())
}
foo(10 + 20) // geçerli


Örneğin:
func foo(@autoclosure f: () -> Void){
print(f())
}
foo(print(“Ok”)) // geçerli
@autoclosure özniteliklendirmesi yapılmış bir fonksiyon ya da metodu fonksiyon ya da closure ile çağıramayız. Örneğin:
func foo(@autoclosure f: () -> Int){
print(f())
}
foo({10 + 20}) // error
Swift’te bir closure kuralı da değer listeleridir (capture value list). Bir closure bildirimin hemen başında köşeli parantezler içerisinde üst bloklardaki değişkenler virgül atomlarıyla ayrılmış bir liste yazılabilir. Bu durumda closure içerisinde bu üst bloktaki değişkenlerin kendileri değil onların closure bloğuna girişteki değerleri kullanılır.
Örneğin:
func foo(){
var a, b: Int
a = 10
b = 20
let f = {
() -> () in print(a + b);
}
a = 30
b = 40
f() // ekrana 70 yazılır
}
foo()
Burada closure’a a ve b’nin kendisi geçirilmiştir. Yani closure çağrıldığında çağrılma noktasındaki değerleri closure kullanır. Ayrıca dış bloktaki değişkenler let değilse closure onları aynı zamanda değiştirebilmektedir. Halbuki biz dış bloklardaki değişkenlerden köşeli parantezler içerisinde bir liste oluşturursak bu durumda closure bildirimine girişte o değişkenlerin değerleri kopyalanarak closure’a aktarılır. Ayrıca clouse içerisinde artık biz bu değişkenlerin değerlerini değiştiremeyiz.
Örneğin:
func foo(){
var a, b: Int
a = 10
b = 20
let f = {
[a, b] () -> () in print(a + b);
}
a = 30
b = 40
f() // ekrana 30 yazılır
}
foo()