itab (arayüz tablosu), Go'da verimli arayüz yönlendirmesini sağlayan temel çalışma zamanı yapısıdır. Somut bir tür ilk kez dolu bir arayüz'e atandığında veya tahmin edildiğinde, çalışma zamanı somut türü arayüz türü ile eşleştiren bir itab oluşturur veya alır. Bu yapı, hızlı tür karşılaştırması için önbelleğe alınmış bir karma içerir ve her arayüz yönteminin dizinini somut türün yöntem uygulamasına eşleyen bir işlev işaretçi tablosu içerir; bu, sonrasında yapılan çağrılarda O(1) arama süresi sağlar.
Bir finansal ticaret platformu, piyasa verisi ayrıştırıcılarının (JSON, FIX, ProtoBuf) dinamik olarak eklenti olarak yüklenebileceği modüler bir mimari gerektiriyordu. Her ayrıştırıcı, Parse() ve Validate() yöntemleri içeren bir Processor arayüzü uyguladı. Sisteminin yönlendirme motoru, eklenti yükleyicisinden opak interface{} referansları alıyordu; bu, saniyede milyonlarca mesaj işlenmeden önce tür tahminleri gerektiriyordu.
Değerlendirilen bir yaklaşım, dize tanımlayıcılarıyla dizinlenmiş işlev işaretçi kayıtlarıydı; bu, herhangi bir arayüz yükünü tamamen atlıyordu. Bu, minimal yönlendirme gecikmesi sağlıyordu ancak derleme zamanında tür güvenliğinden feragat ederek, işlev imzalarının manuel olarak bakıma ihtiyaç duymasını ve Processor sözleşmesine yeni yöntemler eklemeyi zorlaştırıyordu. Ayrıca, her yöntemin ayrı bir kayıt mantığı gerektirmesi nedeniyle kod tabanını parçaladı, bu da uyumlu bir arayüz sağlamak yerine ayrı bir kayıt gerektiriyordu.
Bir diğer alternatif, Go'nun jeneriklerini kullanarak yönlendiriciyi tür kısıtlamaları ile parametreleştirmekti. Bu, arayüz kutulamasını ortadan kaldırdı ve derleme zamanında statik yönlendirme sağladı; ancak jenerikler derleme zamanında çözüldüğü için çalışma zamanı eklenti yüklemesini engelledi ve her ayrıştırıcı türü için yüksek frekanslı yönlendirici kodun monomorfizasyonu nedeniyle ikili dosyanın boyutunu önemli ölçüde artırdı.
Seçilen çözüm, eklenti başlatılması sırasında itab önbelleğinin açıkza ısıtılmasıyla birlikte arayüz tahminlerini kullandı. Her yüklenen eklentiyi Processor arayüzü ile yüklemeden hemen sonra (sıcak yolda) tahmin ederek, çalışma zamanı küresel itab tablosunu önceden doldurdu. Bu, kritik mesaj işleme döngüsünün yalnızca önbelleğe alınmış itab aramalarıyla karşılaşmasını sağladı ve dinamik yüklemenin esnekliğini diğer dillerde sanal tablo uygulamalarıyla karşılaştırılabilir O(1) yönlendirme gecikmesi ile birleştirdi.
Sonuç, temel motor ile üçüncü taraf eklentiler arasında temiz bir ayrım sağlarken, alt mikrosaniye yönlendirme gecikmesi ile saniyede bir milyondan fazla mesajı işleyebilen bir sistem oldu. itab önbellekleme mekanizması, başlangıç ısınma aşamasından sonra dinamik arama cezasını etkili bir şekilde ortadan kaldırdı.
Soru: arayüz'e bir nil somut işaretçi atamak neden hala bir panic yaratabilen bir nil dışı arayüz değeri oluşturur?
Cevap: Bu, arayüz başlığının iki kelime içermesi nedeniyle olur: itab işaretçisi (tip bilgisi) ve veri işaretçisi (değer). *T türünden bir nil işaretçiyi bir arayüz'e atadığınızda, veri kelimesi nil olur, ancak itab kelimesi *T için geçerli tür tanımlayıcısına işaret eder. Bu nedenle arayüz kendisi nil değildir ve tür bilgisi taşır. Bir yöntem çağrıldığında, çalışma zamanı yöntemin adresini bulmak için itab'ı kullanır ve nil alıcı ile çağrıyı gerçekleştirir. Yalnızca o yöntemin alıcıyı nil kontrolü olmadan dereferanslaması durumunda panic gerçekleşir; bu durum, bir arayüz (itab nil olduğunda) ile gerçekten nil bir arayüz arasındaki farktır ve bu durumda yöntem çağrısı hemen panic yapar.
Soru: Çalışma zamanı, ayrı derlenmiş paketlerde veya dinamik olarak yüklenen eklentilerde tanımlanan türler için arayüz yönlendirmesini nasıl işler?
Cevap: Çalışma zamanı, (somut tür, arayüz türü) çiftine göre anahtarlandırılmış küresel bir itab karma tablosu tutar. Yeni bir eklenti yüklendiğinde veya paketler bağlandığında, daha önce görülmemiş bir kombinasyon için tür tahmini yapıldığında, çalışma zamanı arayüz'ün yöntem listesini yineleyerek ve somut türün yöntem kümesindeki karşılık gelen yöntemleri bulmak için ad ve imza karma eşleşmesi kullanarak itab'ı hesaplar. Bu yeni yapılandırılan itab daha sonra küresel önbelleğe eklenir. Herhangi bir goroutine'de sonraki tahminler bu önbelleğe alınmış itab'ı kullanır ve çapraz paket ve dinamik eklenti arayüzü tatmini, iç paket çağrılarıyla aynı O(1) verimlilikte çalışır.
Soru: Aynı arayüz için farklı gömme veya takma adlar nedeniyle tek bir somut türün birden fazla itab temsilcisi olabilir mi?
Cevap: Hayır, belirli bir somut tür ve belirli bir arayüz türü çifti için, çalışma zamanı'nda tam olarak bir tane itab vardır. Go'nun tür sistemi tür tanımlayıcılarını kanonikleştirir; bir tür, farklı içe aktarma yolları veya takma adlar aracılığıyla erişilse bile (örneğin, mypkg.MyType ile other.MyType'ın bir takma ad olduğu durumlarda), bunlar aynı temel tür tanımlayıcısına karşılık gelir. Sonuç olarak, çalışma zamanı, o somut tür için o arayüz'e yapılan tüm tahminler için aynı itab işaretçisini oluşturur veya arar ve tutarlı yöntem yönlendirmesini sağlar; bu, itab alanlarının işaretçi eşitliği karşılaştırmalarının çalışma zamanı içinde güvenilir tür kimlik kontrolü olarak hizmet etmesine olanak tanır.