Dynamic Method Dispatching: Table

0 305

Merhaba, method dispatching serisine daha önce giriş yapmış ve static method dispatching konusuna değinmiştik. Şimdi bir diğer method dispatching yöntemi olan ve bize OOP’ı kazandıran, dynamic method dispatching konusunu ele alacağız.

Static method dispatching, adından da anlaşılacağı üzere çalışacak metotların adreslerinin memory’de önceden bilindiği ve metot çağırıldı anda hangi adreste saklanan komutların işleneceğinin compile-time’da belli olduğu dispatching yöntemiydi.

Dynamic method dispatching ise bir metot çağırıldığı anda, memory’deki hangi adreste yer alan executable-code’un çalışacağına run-time’da dinamik olarak karar verilen dispatching yöntemidir.

Class’ların sahip olduğu metotlar child class’larda override edilip, yeni yetenekler eklenebilir ya da parent class’ta yer alan metot kullanılabilir. Bu durumda gerçekten hangi metodun çalışacağının tespit edilmesi gerekmektedir.

Swift dilinde table ve message dispatching olarak ikiye ayrılmaktadırlar.
Bu yazımda table dispatch konusuna değineceğim.

Table Dispatch (Witness-Virtual Table)

Parent sınıflar için sahip oldukları metotların adreslerinin tutulduğu bir tablo oluşturulur. Ardından child sınıflar için de bu tablonun bir kopyası oluşturulur, override edilmiş metotlar için adres alanı değiştirilir, varsa yeni eklenen metotlar ve adresleri tabloya eklenir.

Bir örnek üzerinden inceleyelim.

Öncelikle “View” adında bir sınıf tanımlayalım ve iki adet metodu olsun.

Ardından “ScrollView” adında başka bir sınıf oluşturalım ve bir metodunu override edip yeni bir metod ekleyelim.

Şimdi her iki sınıf için de oluşan tabloları inceleyelim.

 

 

 

Görüldüğü üzere, Parent sınıftan override edilmeden kullanılan “hide” metodunun adresi iki tablo için de aynı. override ettiğimiz “show” ve yeni eklediğimiz “addScroll” metotları için ise yeni adresleri kayıt edilmiş durumda.

Şimdi basit bir kod parçası yapalım ve run-time’da ne olduğuna bakalım.
Son haliyle kod bloğumuz aşağıdaki gibi olacaktır.

Son satır özelinde işlemcimizi inceleyelim.

1) scrollView nesnesine ait tablo 0xCA0 adresinden okunur.
2) Çağırılacak olan “show” fonksiyonu için 0xCA4 adresi okunur.
3) 0xCA4 adresine zıplanır.
4) Tekrar 0xCA0 adresine dönülür.
5) “addScroll” metodu için 0xCA8 adresi okunur.
6) 0xCA8 adresine zıplanır.

Burada meydana gelen, okuma-zıplama işlemleri sebebiyle dynamic dispatching, static dispatching’den daha maliyetli ve yavaş olmaktadır. Bu sebeple mümkün olduğunca derleme anında hangi metodun çalışacağının belirlenebilmesi için static method dispatching kullanılmaya çalışılır. Örneğin hiç Child’ı oluşturulamayacak sınıfları “final” olarak tanımlamamız iyi bir deneyim olacaktır.

Swift’te sınıfların ve protokollerin ilk tanımlandığı alanda oluşturulan metotlar, spesifik keywordler kullanılmamışsa (final, static, @objc vb.) table method dispatching yöntemini kullanırlar.

Bir sonraki yazımda Message Dispatching konusuna değineceğim.

Mutlu kodlamalar 🙂

Yorum yaz

Email adresiniz yayınlanmayacaktır.