Haftalık C++ 36 – decltype, std::is_same, std::declval

Photo by Kelly Sikkema (unsplash.com)

C++ 11 ile gelen yeni kabiliyetlere bakmaya devam ediyoruz. Evet, bir kaç yazı sonra bitecek demiştim, lakin işle işle bitmiyor güzellikler 🙂 Gerçi fazla da kalmadı.

Bugün değineceğim kabiliyetlerden ilki “decltype“. Aslında bu, C++ 11 ile gelen yeni bir anahtar kelime. İsmine bakınca, bir tip tanımlama gibi gelse de (declare a type?), aslında geçirilen parametrenin tipine kullanmaya yardımcı olmak için sunulan bir mekanizma. Peki neden “typeid” gibi daha açıklayıcı bir anahtar kelime kullanmıyoruz. Çünkü typeid zaten var 😀 ama buna ileride değineceğim.

Temelde bu anahtar kelime ile, geçirilen birimin ya da ifadenin tipi dönülebilmekte ve bunu da tipin ihtiyaç duyulacağı yerlerde kullanabiliyorsunuz. Kafaları daha fazla karıştırmadan, her zaman yaptığımız gibi örnek bir kod üzerinden kabiliyete göz atalım. Yine örneği, C++ referans sayfasından alıyorum, elbette biraz sosluyoruz 😉

Yukarıda parantez kullanımı ile aslında temsil edilen tipin nasıl değiştiğine ufak bir örnek verdik. Bu kullanım, bununla sınırlı değil. Aşağıdaki “değer kategorisine” göre, declype(t) için dönülen tiplere örnekleri görebilirsiniz. Burada t’nin tipinin T olduğunu farz edelim:

  • T, eğer t prvalue ise,
  • T&, eğer t lvalue ise,
  • TT&&, eğer t xvalue ise.

Daha önce l-value ve r-value’ye değinmiştim. Diğerlerine burada girmeyeceğim ama meraklı okuyucularım, https://en.cppreference.com/w/cpp/language/value_category sayfasına göz atabilirler. Bunlar, örnekler ile gayet güzel açıklanmakta.

Şimdi gelelim “typeid” anahtar kelimesine. typeid ile decltype anahtar kelimeleri birbirlerine benzer olsalar da, çok temel farklılıkları var. typeid, ilgili tipin çalışma zamanında (RTTI mekanizması) tipini öğrenmeye yönelik olsa da, declype ile derleme zamanında bu tipe ilişkin işlemleri gerçekleştirebiliyorsunuz. typeid’ye biraz mesafeli yaklaşılmakta, özellikle aviyonik ya da emniyet kritik yazılımlar geliştiriyorsanız, uzak da durmalısınız (keza çoğu zaman bu özellik kapatılmakta).

Peki, tipleri aldık güzel. İki tipin aynı olup/olmadığını nasıl kontrol edeceğiz. Onun için de <type_traits> başlık dosyası içerisinde sunulan std::same‘i kullanabilirsiniz. Hemen bakalım:

Tahmin edebileceğiniz üzere bu anahtar kelimeler her ne kadar yukarıda gösterdiğim şekilde de kullanılabilse de, asıl endam ve güzelliklerini template’lar ile kullanımlarında ortaya koyuyorlar. Kaynaklar kısmına eklediğim O’Reilly’nin kitabında bunun istemediğiniz kadar detayına inmekte 🙂

Son bahsedeceğim eleman std::declval. Bu da <utility> başlık dosyası içerisinde tanımlanmakta. Bunun kullanımı, yukarıdakilere göre ilk etapta net olmayabilir. Ben yine de açıklamaya çalışayım, örnek ile de netleştiririz. Yukarıda da bahsettiğim gibi, tipleri referans olarak dönebilmek için  ilgili tipin nesnesini (decltype(a))  ya da ifadesini (decltype(5)) decltype’a geçirmeniz gerekiyor. Kısaca, std::declval ile, herhangi bir tipin nesnesini kullanmadan, o tipe ilişkin rvalue referans dönebilirsiniz.

std::declval, çoğunlukla, template’larda template parametresi, yapıcı içermediği fakat ilgili parametre tipine ilişkin dönüş değerine de ihtiyaç olduğu durumlarda da kullanılmaktadır. Hemen, std::declval sayfasindan bir örneğe bakalım:

Evet sevgili yazılımperver dostlarım, yine bir yazımın sonuna geldik. Bir sonraki yazımda görüşmek dileğiyle kendinize çok iyi bakın, bol sağlıklı ve kodlu günler 😀

Kaynaklar:

Bir cevap yazın

E-posta hesabınız yayımlanmayacak. Gerekli alanlar * ile işaretlenmişlerdir

This site uses Akismet to reduce spam. Learn how your comment data is processed.