Swift’ te Değer Türü ve Referans Türü

Evren Yaşar
NSAnkara
Published in
5 min readMar 7, 2018

Bu makalede Swift deki değer türü (value type) ve referans türü (reference type) arasındaki farklar incelenecektir. İki kavram detaylı şekilde incelenerek tanınması, güçlü ve zayıf yönlerinin belirlenmesi amaçlanmaktadır. RAM (Random Access Memory) kullanımında ki (memory manage) etkileri incelenecektir.

Referans Türü

Referans türü; Verinin tüm örnekler için aynı kopyayı paylaşması olarak isimlendirilebilir. Referans türleri hafızanın heap kısmında saklanmaktadır.

Refarans türüne örnek;

KisiClass, basit bir class yapısıdır. 9. Satır içerisinde “KisiClass” sınıfının bir örneği “d1” değişkenine atanmıştır. “d1” değişkeni içerisinde yer alan kişi adı “Evren” olarak belirlenmiştir. 10. satırda “d2” adında yani bir değişken oluşturulmuştur. “d2” değişkeni içerisinde daha önce oluşturulmuş olan “d1” değişkeni atanmıştır(Shallow Copy) .

12. Satır da ise “d1” isimli değişkenin “adi” parametresi “Necati” olarak ayarlanmıştır.
14. satırda ise sonuç ekrana yazılmıştır; //D1:Necati, D2:Necati

Yalnızca “d1” değişkenin içeriği belirlenmiş olmasına ragmen “d2” değişkeni de “d1” değişkeni ile aynı anda değişmiştir. Grafik ile gösterimi aşağıdaki şekildedir;

Şekil 1

Referans türleri memory üzerinde heap kısmında tutulmaktadır. Oluşturulan değişkenler stack aracılığı ile heap’ e ulaşırlar. Burada iki değişkende aynı heap adresini barındırmaktadır.

Şekil 2

Şekil 2’ de yer alan örnekte görüleceği üzere “d1” ve “d2” değişkenleri heap üzerinde aynı adresi göstermektedir, Bu sebeple “d1” veya “d2” içerisinde yapılacak olan değişiklikler aynı anda her iki değişkeni de etkilemektedir. Değer türleri ve referans türleri arasındaki tüm farklar bu sebeple meydana gelmektedir.

Değer Türü

Verinin tüm örnekleri için benzersiz birer kopya oluşturması Değer Türü olarak isimlendirilir. Değer türleri memory’ nin stack kısmında saklanmaktadır.

Swift’ te String, Int, enum, Bool, Array, Dictionary, struct yapılarının tamamı değer türündedir. Class hariç herşey değer türü olarak nitelendirilebilir. Daha iyi anlaşılabilmesi için örnekler içerisinde struct kullanılacaktır. Bu sayede struct ve class arasında yer alan farklarda görülmüş olacaktır.

Değer türü örneği olarak aşağıda yer alan kod parçacığı incelenebilir;

KisiStruct, bir struct yapısıdır. 9. satırda “KisiStruct” örneği “f1” değişkenine atanmıştır. “f1” değişkeni içerisinde kişinin adi “Evren” olarak belirlenmiştir. 10. satırda “f2” adında yani bir değişken tanımlanmıştır. “f2” değişkenine daha önce tanımlanan “f1” değişkeni atanmıştır (Deep Copy).

12. satırda ise f1 isimli değişkenin adi parametresi “Necati” olarak ayarlandı.
14. satırda sonuç ekrana basıldı; // F1:Necati, F2:Evren

“f1” değişkeninin özelliklerinden biri değiştirildiğinde “f2” değişkeninde bir önceki class örneğinde olduğu şekilde herhangi bir değişiklik olmamıştır. Değer türleri ile referans türleri arasında ki farklılık bu şekilde gösterilebilir.

Grafik üzerinde gösterimi aşağıda ki şekildedir;

Şekil 3

Değer türleri memory’ nin stack kısımlarında tutulmaktadır. Stack üzerinde her bir değişken için yeni birer kopya oluşturulabilir. Stack, heap’ e göre daha hızlı olmasına rağmen boyutu daha küçüktür.

Şekil 5

Şekil 4 içerisinde “f1” değişkeninin oluşturulan kopyasının stack üzerinde nasıl saklandığını gösterilmiştir. Tüm kopyalar ayrı birer alanda temsil edilmektedir.

Değişebilirlik (Mutability)

Değer türü ve referans türlerinin değiştirilebilirlik konusunda daha iyi anlaşılabilmesi için variable değiştirilebilirliği ve instance değiştirilebilirliğinin incelenmesi gerekmektedir.

Değer türlerinde variable ve instance kavramları birbirine mantıksal olarak bağlıdır. Değiştirilemez bir struct oluşturulduğunda, buna bağlı olarak struct’ ın özelliği olan değerde otomatik olarak değiştirilememektedir.

Yukarıda yer alan örnekte Sehir adında bir struct oluşturulmuştur. Bu struct’ a plaka adında değiştirilebilir (var) özelliği eklenmiştir. Sehir struct’ ı ankara adlı bir sabite (let) atanmıştır. Burada Sehir’ in plaka özelliği değiştirilebilir olduğu halde hata alınmıştır. Bunun nedeni değer türlerinin variable ve instance larının mantıksal bir bağla bağlanmasıdır.

Referans türlerinde variable ve instance kavramları birbirine bağlı değildir. Değiştirilemez bir class oluşturulduğunda, bu durum class ın özelliklerini değer türünde olduğu şekilde etkilememektedir. Birbirinden tamamen bağımsızdırlar.

Struct örneği aynı şekilde class ile değiştirilir.

Yukarıdaki örnekte Sehir adında bir class oluşturulmuştur. Oluşturulan class’ a plaka adında değiştirilebilir (var) özellik eklenmiştir. Sehir class’ ının ankara adında bir sabite (let) atanmıştır. Daha sonra satır 9 da ankara instance’ nın plaka özelliği güncellenmiş ve herhangi bir hata alınmamıştır. Aynı işlem değer türlerinde yapıldığında hata alınmaktadır.

Avantaj ve Dezavantajlar

Uygulama geliştirme işleminde struct veya class kullanımı geliştiricinin insiyatifindedir. Geliştirilen sistemin daha performanslı çalışması ve bug oluşumunun engellenebilmesi için en doğruyu seçmek hayat kurtarıcı bir yöntemdir. Değer türü ile referans türlerinin avantaj ve dezavantajları aşağıdaki şekilde sıralanabilir.

Değer Türü Artıları

  1. Verimlilik : Değer türleri Ram’ de stack üzerinde yer almaktadır. Stack’ a ulaşmak ile heap’ e ulaşmak arasında ciddi performans farklı bulunmaktadır. Ancak burada stack alanı küçük olduğundan daha dikkatli kullanmak gerekmektedir.
  2. Thread Safe : Değer türleri kopyalandığında birbirinden bağımsız örnekler oluşmaktadır. Özellikle Paralel Programing ‘ e girildiğinde aynı örnek üzerinden birden fazla thread işlem yapılırsa, sonuç doğru çıkmamakta veya sistemin kilitlenmesine neden olmaktadır.
  3. Memory Leaks : Swift de verilerin temizlenme işini Automatic Referance Counting (ARC) üstlenir. Örneği oluşturulan sınıfın kaç kez kullanıldığı bilgisini tutar. Referans verisi 0 (sıfır)’ a eşitlendiğinde o instance’ ı temizlemektedir. Değer türlerinin referansları yoktur. Değer türünü kullanan nesne kapatıldığında kendini silmektedir. Bu özellik sayesinde Memory Leak gerçekleşmemektedir.
  4. Tahmin edilebilirlik : Değer türleri her seferinde yeni bir kopya üzerinde işlem yapmaktadır. Daha önce nerede kullanıldığı hiç önemli değildir. Referans türlerinde kullanılan veri üzerinde daha önce işlem yapılmışsa, size istediğiniz değerleri döndürmemektedir. Değer türlerinde bu sorunla karşılaşılmamaktadır.

Değer Türü Eksileri

  1. Kalıtım : Değer türlerinde kalıtımdan yararlanılamamaktadır. Kalıtımdan yararlanılması, referans değerinin tutulabilmesidir.
  2. Büyük veri : Elinizde yer alan veriyi farklı metodlarda veya class larda işlemek isteyebilirsiniz. Verinin sürekli yeni kopyasının oluşturulmasından dolayı farklı metodlarda veya class larda işlenmesi mümkün değildir. Örneğin Review sitesi yapılırken App açılması işleminde elinizde yer alan 10k mekan listesinin olduğunu varsayalım. Bu listede etiket bilgileri eksik. Etiket verileri ile mekan verileri birleştirilirken sürekli kopyası oluşacağından Ram üzerinde şişmeler oluşacaktır. Kullanımı çok daha zorlaşacakdır.
  3. Metod-Parametre sorunu : Değer türleri her seferinde yeni kopya oluşturduğundan, metoda parametre olarak gönderildiğinde yeni bir kopyası oluşmaktadır. İşlenmesi gereken veri sabit kalmaktadır. Yaşanan bu durumun çözümü için inout yapısı incelenebilir. İnOut yapısı için aşağıda yer alan örnek incelenebilir.

Referans Türü Artıları

  1. Ortak işlem : Referans türlerinin tüm instanceları aynı veri üzerinde işlem yapmaktadır. Elinizde büyük bir verinin olduğunu düşünelim. Sürekli bu veri üzerinde işlem yapılacaksa aynı referans kullanılarak işlem kolaylılığı ve hafızada alan kazanılmaktadır. Özellikle büyük frameworklerin facade kısımları class ile yazılmaktadır.
  2. Kalıtım : Değer türlerinde kalıtım kullanılamamakta iken referans türlerinde kalıtımdan faydalanılabilmektedir.
  3. Metod-Parametre : Eğer bir metod’ a parametre gönderip, bu parametre üzerinde işlem yapılması isteniyorsa, oluşturulan veri örneğinin referans türünde olması gerekmektedir.

Referans Türü Eksileri

  1. Memory Leak : Swift’ te verilerin temizlenme işini Automatic Referance Counting (ARC) üstlenir. ARC siz bir nesnenin instance ’ını oluşturulduğunda, ARC içindeki referans sayısı o sınıf için 1 artmaktadır. Eğer instance’ ı oluşturulan sınıfın ARC üzerindeki referans sayısı 0 (sıfır)’ a eşitlenmezse, sınıf silinmemektedir. Özellikle closer yapılarında self ön eki ile özelliklere ulaşılırken sık sık görülmektedir. Bir sonraki yazıda bu konuyu detaylı olarak incelenecektir.
  2. Thread Safe : Veri tabanı bağlantısı gibi işlemlerde class yapısından uzak durulması gerekmektedir. Aynı class ı aynı anda birden fazla thread kullanırsa, veride bozulmalara neden olacaktır.

Bu makalede Değer türleri ile Referans türleri incelenmeye çalışılmıştır. Makale Swift programlama dilini anlayarak yazmak ve memory manage konusuna giriş düzeyinde bilgi verilebilmesi amaçlanmıştır.

Bir sonraki makalede memory manage konusunun daha detaylı incelemesi yapılacaktır. Memory Manage’ in daha iyi anlaşılabilmesi, referans ve değer türlerinin örnekler üzerinden detaylandırılarak incelenmesi sağlanacaktır.

--

--