ProgramlamaGömülü C geliştirici

C dilinde geri çağırma işlevlerinin (callback functions) nasıl gerçekleştirildiğini ve çalıştığını tanımlayın. Bu tür işlevleri kütüphaneler geliştirme veya API ile etkileşimde nasıl doğru bir şekilde tanımlayıp kullanmalıyız?

Hintsage yapay zeka asistanı ile mülakatları geçin

Cevap

Geri çağırma işlevleri (callbacks), adreslerinin diğer bir işlevin argümanı olarak gönderildiği işlevlerdir. Bu, olay işleyicilerini, kullanıcı algoritmalarını ve eklentileri gerçekleştirmeyi sağlar.

Callback işlevinin tanımı:

  1. Uygun işlev gösterici tipinin tanımlanması:
typedef void (*callback_func_t)(int);
  1. İşleyici işlevinin gönderilmesi:
void process(callback_func_t cb) { // ... cb(42); // geri çağırmayı çağır } void handler(int n) { printf("İşlenmiş sayı: %d ", n); } int main() { process(handler); return 0; }

İpuçları:

  • Pointer tipleri için açık bir typedef kullanın, kod daha okunabilir olur.
  • Geri çağırma işlevinin imzasının beklenenle eşleştiğinden emin olun.
  • Yerel olarak alınmamış veya serbest bırakılmış işlevleri göndermekten kaçının.

Kandırmaca soru

Geri çağırma olarak imza uyuşmazlığı olan bir işlev gönderilebilir mi?

Yanlış yaygın cevap: "Evet, C buna izin verir, eğer tür dönüşümü açıkça tanımlanırsa".

Doğru cevap: Ancak, resmi tür dönüşümü mümkün olsa da, böyle bir işlevin çağrılması belirsiz davranışa yol açar — parametreler yanlış değerlerle gönderilebilir, yığın bozulabilir.

Tehlike örneği:

typedef void (*cb_t)(int); void wrong_cb(double d) { printf("%f ", d); } void call(cb_t f) { f(123); } int main() { call((cb_t)wrong_cb); } // TEHLİKE: imzalar farklı

Konuyla ilgili bilgi eksikliğinden kaynaklanan gerçek hata örnekleri


Hikaye

Bir gömülü projede, sıralama işlevi, çok dar bir imzaya sahip bir karşılaştırma işlevinin göstericisini alıyordu. Bu, sıralama hatalarına ve parametrelerin yanlış iletilmesi nedeniyle bellek bozulmalarına yol açtı.

Hikaye

Bir grafik motoru kütüphanesinde, geri çağırmalara dayalı bir olay mekanizması uygulanmıştı, ancak bazı geri çağırmalar, zaten serbest bırakılmış dinamik kütüphanelerden yerel işlevlere rastgele başvuruyordu. Bu da geçersiz adreslerle karşılaştıklarında çökme oluşturdu.

Hikaye

Bir çapraz platform sistemi geliştirirken, yazar geri çağırma işlevleri için yanlış çağrı konvansiyonunu tanımlamıştı. Bu, bir işletim sisteminde görünmezdi, ancak başka birinde C kütüphanesinden geri çağırmalar yapıldığında programın çökmesine yol açıyordu.