gokayburuc

Rust - Closures as Parameters in Functions

Closure'ları Parametre Olarak Kabul Eden Fonksiyonlar

Konu: Fn() Trait Bound'u ile Closure ve Fonksiyon'u Birleştirmek

Bu kod, bir fonksiyona closure ile sıradan fn'nin aynı jenerik parametre üzerinden nasıl geçirildiğini gösteriyor.


Parça 1: Closure Üreten ve Çağıran Public Fonksiyon

// Bu fonksiyon "public": dış modüllerden de çağrılabilir.
pub fn execute_closure_input_function() {
    // Bir closure tanımlıyoruz: argümansız, değer döndürmüyor.
    // Derleyici bunun için ANONİM bir tip üretir ve Fn trait'ini implement eder.
    let closure = || println!("I'm a closure!");

    // Aynı fonksiyona önce closure, sonra sıradan bir fn geçiriyoruz.
    // İkisi de Fn() trait'ini sağladığı için kabul edilir.
    call_this(closure); // closure anonim tiptir
    call_this(sample_function); // fn pointer ise fn item tipindedir
}

Parça 2: Sıradan Fonksiyon

// Sıradan (closure olmayan) bir fonksiyon.
fn sample_function() {
    println!("I'm a function!");
}

Parça 3: Fn() Bound'lu Jenerik Çağırıcı

// "call_this" herhangi bir ÇAĞRILABİLİR şeyi kabul eder,
// ama şartı var: argümansız çağrılabilen ve bir şey döndürmeyen (Fn()).
// F generic olduğu için closure'ın anonim tipini de kabul edebilir.
fn call_this<F: Fn()>(f: F) {
    f(); // gelen şeyi çağırıyoruz.
}

Çıktı

I'm a closure!
I'm a function!

Özet ve Sonuç

Parçalar arası ilişki ve veri akışı:

  1. Parça 1'de closure, Parça 2'de fn item üretilir; ikisi de Parça 3'ün F: Fn() parametresine taşınır (ownership call_this'e geçer).
  2. call_this gelen değerin tipini bilmez; yalnızca Fn() sözleşmesine güvenir ve f() ile çağırır. Bu, "struct'lar yerine davranıştan programlama" (duck typing'in derleme zamanı garantili hali) anlamına gelir.
  3. Önceki makaledeki execute_closure_output_parameter closure üretip döndürüyordu; bu örnekteki execute_closure_input_function ise closure'ı parametre olarak kabul ediyor. İkisi birlikte Rust'ta closure'ların birinci sınıf değerler olduğunu kanıtlar: üretilebilir, döndürülebilir, taşınabilir ve başka fonksiyonlara argüman olarak verilebilir.

Öğrenilecek ana ders: Fonksiyona "çağrılabilir" kabul ettirmenin idiomatik yolu ham fn pointer değil, Fn/FnMut/FnOnce trait bound'lu jenerik parametredir. Bu sayede hem closure hem fonksiyon aynı API'yi paylaşır.

#rust