Objective-C ile Nesne Yönelimli Tasarım Prensipleri

Objective-C ile Nesne Yönelimli Tasarım Prensipleri

Objective-C ile Nesne Yönelimli Tasarım Prensipleri kitabı, nesne yönelimli programlama ve tasarım prensipleri hakkında kapsamlı bir rehberdir Kitap, temel konuları kapsamakla birlikte, gelişmiş stratejileri ve teknikleri de içermektedir Bu rehber sayesinde, iOS ve macOS uygulama geliştirme becerilerinizi geliştirebilir ve daha iyi bir yazılım mimarisi oluşturabilirsiniz

Objective-C ile Nesne Yönelimli Tasarım Prensipleri

Objective-C, Apple'ın işletim sistemi olan iOS ve macOS'taki uygulamaların geliştirilmesinde kullanılan bir programlama dilidir. Bu dil, nesne yönelimli programlama (Object-Oriented Programming - OOP) prensiplerine uygun olarak yazılan kodları desteklemektedir.

OOP, programlama dilindeki en önemli paradigmalardan biridir ve nesnelerin özelliklerine ve davranışlarına odaklanır. Objective-C, bu prensipleri kullanarak kodların daha kolay anlaşılır, güncellenebilir ve genişletilebilir olmasını sağlarken, geliştiricilere daha verimli bir çalışma imkanı sunar.

Bu yazıda, Objective-C dilinde nesne yönelimli tasarım prensiplerini öğrenerek, kodlarınızın daha kapsamlı ve daha iyi organize edilmiş olmasını sağlamak için ne yapmanız gerektiğini öğreneceksiniz. Bunun yanı sıra nesne yönelimli tasarım desenlerini tanıyarak, yazılımınızı daha da geliştirebilirsiniz.


Nesne Yönelimli Programlama (OOP) Nedir?

Nesne Yönelimli Programlama (OOP) bir programlama paradigmalarından biridir. OOP'de, programlama işlemleri bir nesnenin içinde gruplandırılır. Her nesnenin kendi özellikleri (alanları) ve davranışları (metodları) vardır. Nesne yönelimli bir yaklaşım, problemi bir dizi nesne olarak ele alan ve nesnelerin birbiriyle olan etkileşimlerini modelleyen bir tasarım şeklidir.

OOP'nin önemi, büyük ölçekli yazılımların geliştirilmesinde çok faydalı olmasıdır. Nesne yönelimli tasarım, kodun yeniden kullanılabilirliğini artırır ve programlama sürecini daha kolay hale getirir. OOP ayrıca kodun okunabilirliğini artırır, bakımını kolaylaştırır ve kodun performansını artırarak daha hızlı çalışmasını sağlar.

OOP kullanımı için, bir dizi sınıf oluşturulur. Sınıflar, açıklayıcı adları olan nesnelerin bir koleksiyonudur. Her sınıf, özellikleri ve davranışları belirleyen bir tasarıma sahiptir. Özellikler verileri depolar, metodlar ise sınıflar arasında davranışları sağlar. Nesne arayüzleri, sınıfların birbirleriyle nasıl etkileşime gireceği ile ilgili kuralların belirlenmesine yardımcı olur.

OOP, bir kodlama disiplini olarak oldukça önemlidir. OOP kullanarak yazılan kod, genellikle daha düzenli, tutarlı ve öngörülebilir bir şekilde çalışır. Ayrıca, OOP'nin kullanımı, kodun yeniden kullanılabilirliğini ve değiştirilebilirliğini de artırır.


Temiz Kod Yazmanın Önemi

Birçok yazılım geliştiricisi, programlama dillerinde yaptığı hatalar nedeniyle bozuk kod yazabilir. Bu nedenle, temiz kod yazmak, kod kalitesini artırarak verimliliği de artırır. Temiz kod yazmanın önemini ve nasıl yapabileceğinizi aşağıda bulabilirsiniz.

Temiz kod yazarak, kodunuzun okunabilirliğini ve anlaşılırlığını artırabilirsiniz. Bu, başka bir programcının kodunuzu anlamasını kolaylaştırır ve böylece ürünlerinizi daha hızlı geliştirebilirsiniz. Ayrıca, temiz kod yazmanın programlama sürecini kolaylaştırdığını belirtmek de önemlidir. Kod okunabilirliği, genellikle düşük seviyeli bir kodlama yapmak istediğinizde daha da önemli hale gelir.

Temiz kod yazmak aynı zamanda, değişiklikler yapmak istediğinizde daha kolay hissetmenize yardımcı olabilir. Özellikle daha önceki kodlamalarınıza yeni bir şeyler eklemeniz gerektiğinde, temiz kod yazmak, düzenlemeleri daha hızlı ve kolay yapmanızı sağlar.

Temiz kod yazmanın bir diğer avantajı, daha az hata riski taşımasıdır. Kodunuzun okunabilirliği ve anlaşılırlığı arttığında, kodda meydana gelen hataları daha kolay tespit edebilir ve düzeltebilirsiniz. Bu ise ürünlerinizin kalitesini ve güvenilirliğini artırır.

Bununla birlikte, temiz kod yazmak bazen zor olabilir. Bu nedenle, kodunuzu yapılandırarak düzenli bir şekilde tutabilir ve hatta mümkün olduğunda otomatikleştirebilirsiniz. Ayrıca, kodu sık sık kontrol ederek gereksiz yere uzun belirteç dizileri ve kod yapısı oluşturmayın. Kodunuzu mümkün olduğunca basit tutun ve ayrıntılara fazla takılmayın.

Özetle, temiz kod yazmak, kodunuzun okunabilirliğini artırabilir, programlama sürecini kolaylaştırabilir, değişiklikleri daha kolay hale getirebilir ve daha az hata riski taşıyabilir. Bu nedenle, mümkün olduğunda temiz kod yazmayı hedefleyin.


Kod Okunabilirliği

Kodun okunabilirliği bir yazılımın işlevselliğinin yanı sıra programcılar arasındaki çalışma sürecinde de önemlidir. Kod okunabilirliğinin yüksek olması, yazılımın bakımının ve değiştirilmesinin daha kolay olmasını sağlar.

Bir yazılımın anlaşılırlığının artması için kodun düzenli biçimde yazılması gereklidir. İlgili kod bölümleri birbirinden ayrılmalı, kodun açıklamaları ve yorum satırları yer almış olmalıdır. Ayrıca, kodun tekrarlanan bölümlerinden kaçınılmalıdır. Bu da DRY prensibine uygun olarak yapılabilir.

Kod okunabilirliğinin artırılması, yazılım geliştirme sürecinde zaman ve maliyet tasarrufu sağlar. Ayrıca, projede çalışan programcılar arasında bilgi paylaşımına olanak tanır. Kodun temiz yazılması, programlama sürecini kolaylaştırır ve hataların yapılmamasına yardımcı olur.

Tablo 1'de kod yazarken dikkat edilmesi gereken bazı öğeler listelenmiştir:

Öğe Açıklama
Kod düzeni Kod bölümlerinin birbirinden ayrılması, belirli bir standartta yazılması
Açıklama ve yorumlar Kod satırlarının anlamı ve işlevi hakkında açıklamaların yazılması
DRY prensibi İstenmeyen tekrarlanan kod bloklarının önlenmesi
Kod kalitesi Kodun test edilebilir olması, hataların önlenmesi ve kapsamlı bir belgelendirmeye sahip olması

Yukarıda belirtilen öğelerin hepsi, kod yazarken dikkat edilmesi gereken önemli noktalardandır. Bu öğelerin uygulanması, kodun okunabilirliğini ve yazılım kalitesini arttıracaktır.


DRY Prensibi

DRY Prensibi veya sıklıkla söylendiği gibi "Don't Repeat Yourself" prensibi, kod içinde aynı şeyleri tekrar etmemenizi, aynı kodun birden fazla yerde yazılmamasını ve kod tekrarlarının önlenmesini savunan bir nesne yönelimli tasarım prensibidir.

Bu prensip, kodun anlaşılırlığını ve okunabilirliğini artırırken, bakımını ve genişletilmesini de kolaylaştırır. Aynı kodun tekrar tekrar yazılması zaman alıcı ve hatalı olabilir, bu nedenle DRY prensibi yazılım geliştirme sürecini daha verimli hale getirir.

Bunun yanı sıra, DRY prensibi kodun yeniden kullanılabilirliğini artırır. Kod parçalarını yeniden kullanmak, yeni özellikler eklemek ve değişiklikler yapmak için karmaşık kod bloklarına bakmadan önce kod tekrarlarının aranmasına gerek kalmaz.

DRY prensibinin uygulanmasıyla birlikte, kodun daha az hata yapma olasılığı da artar. Her bir kod parçası sadece bir defa yazıldığından, tüm düzenlemeler daha tutarlı ve güvenilir hale gelir.

Bu prensip ayrıca, projelerde çalışan geliştiricilerin birbirleriyle uyum içinde çalışmalarına da yardımcı olur. Projede birçok kişi çalışabilir ve DRY kod, her biri tarafından anlaşılması kolay ve düzenli bir şekilde yönetilebilir.


Nesne Yönelimli Tasarım (OOD) Prensipleri

Nesne Yönelimli Tasarım (OOD) prensipleri, yazılımda kalite, tutarlılık ve sürdürülebilirlik sağlamak için kullanılan belirli kuralları ifade eder. OOD prensiplerine uygun kodlar, daha kolay anlaşılabilir, bakımı daha kolay, genişletilebilir, test edilebilir, anlaşılır ve az bağımlı olma özellikleri gösterir. Bu prensipler, tercih edilen ve kanıtlanmış yapılardır. OOD prensipleri, kod yazma sürecinde doğru, etkili ve verimli bir şekilde ilerlemenize yardımcı olabilir.

OOD prensipleri, yazılım tasarımına yön vermek ve kod kalitesini artırmak için çeşitli kategorilerde düzenlenmiştir. Bu prensipler, tek sorumluluk, açık kapalı, Liskov'un yerine koyma, arayüz ayrımı ve bağımlılıkların tersine çevrilmesi prensipleri olarak bilinir.

Tek Sorumluluk Prensibi (SRP) ile bir sınıfın tek bir sorumluluğu olmalıdır. Bu, kodun okunabilirliğini ve bakımını kolaylaştırır. SRP, yazılımın anlaşılmasını ve olası değişikliklerin orijinal kodun diğer bölümlerine veya sınıflarına müdahale etmeden yapılabilmesini sağlar.

Açık Kapalı Prensibi (OCP), bir sınıfın değiştirilmeden önce veya sonra derlenebilir olmasını sağlayan bir prensiptir. Bu, uyumluluğun ve sürdürülebilirliğin artmasına yardımcı olabilir. Bu prensip, modül bazlı yazılım tasarımına izin verir. Bu sayede değişikliklerin sadece ilgili modüllerde yapılması gerektiği avansı sağlanır.

Liskov'un Yerine Koyma Prensibi (LSP), bir alt sınıfın üst sınıfın yerel nesnelerine eşdeğer davranışlar sergilemesini sağlar. Bu prensip, kodun doğru çalışmasını sağlar ve genellikle nesne yönelimli tasarımın temel taşı sayılır.

Arayüz Ayrımı Prensibi (ISP), bir arayüzün, ihtiyaç duyulmayan yöntem ve özellikler içermemesi prensibini ifade eder. Bu prensip, kodun bakımının ve anlaşılabilirliğinin kolaylaşmasına yardımcı olur.

Bağımlılıkların Tersine Çevrilmesi Prensibi (DIP), kodda bağımlılıkların sınırlanmasını ve daha az bağımlı olma durumunun sağlanmasını amaçlayan bir prensiptir. DIP, nesne yönelimli tasarımda modülerlik ve sürdürülebilirlik sağlamak için önem lidir.


SRP: Tek Sorumluluk Prensibi

SRP, Tek Sorumluluk Prensibi, bir sınıfın yalnızca tek bir sorumluluğu olması gerektiğini ifade eder. Bu prensip, kodun daha okunabilir hale gelmesini ve bakımının kolaylaşmasını sağlar. Her sınıfın yalnızca tek bir sorumluluğu olduğunda, diğer sınıfların bu sorumluluğu tetiklememesi ve sınıfın kendisini değiştirerek uygulanabilecek değişiklikler için daha az etkilenmesi mümkündür.

Bu prensibi uygulamak için, önce sınıfın sorumluluklarının tanımlanması gerekir. Daha sonra, sınıfın sadece bu sorumlulukları yerine getiren kodlar içermesi sağlanmalıdır. Bu prensipi uygulamak, kod yapılarının mantıklı bir şekilde bölünmesine olanak tanır ve bakım sürecini karmaşık olmayan küçük parçalara ayırır.

Faydaları Zararları
  • Kodun daha okunabilir hale gelmesi
  • Kodun bakımının kolaylaşması
  • Daha az hataya neden olan kodlar yazmak
  • Daha fazla sınıf uygulaması gerekebilir
  • Kodun bölünebilirliği konusunda zorluklar yaşanabilir

SRP, ISO 9001: 2015 kalite yönetim sistemleri standardının 4. bölümünde yer almaktadır. Bu nedenle, bu prensibin birçok sektörde uygulanması gerekmektedir. SRP'nin kullanımı, kodun anlaşılabilirliğini ve bakımını kolaylaştırarak yazılımın kalitesini arttırır. Bu prensipi uygularken, sınıflarınızın sorumluluklarını açıkça tanımlayın ve bu sorumluluklarla ilgili kodları sınıfın içindeki tek bir yöntemde birleştirmeye çalışın.


Yüksek Cohesion

Yüksek cohesion (tutarlılık) nesne yönelimli programlama prensipleri arasında en önemli olanlardan biridir. Cohesion, bir sınıfın içerdiği özelliklerin ne kadar uyumlu olduğunu ifade eder. Yani bir sınıf içerisinde yer alan özelliklerin birbiri ile tutarlı olması gerekmektedir. Bunun nedeni, sınıfın işlevselliğinin kolay anlaşılabilmesi ve sınıfın güncellenmesinin diğer sınıflara zarar vermeden yapılabilmesidir.

Yüksek cohesion sağlamak için bir sınıfın yapması gereken işlemleri bir arada toplamak gerekir. Böylece, sınıfın özellikleri ve işlevleri arasında daha az bağlantı olduğundan sınıfın okunabilirliği ve anlaşılabilirliği artar. Ayrıca, sınıfın yapısını daha kolay değiştirebilirsiniz. Örneğin, bir sınıfın özelliklerini değiştirmeniz gerektiğinde sınıfın işlevsel bütünlüğü bozulmadan işlem yapabilirsiniz.

Yüksek cohesion elde etmek için sınıfların işlevleri ne kadar çok benzer ise o kadar iyi olacaktır. İşleri kontrol eden sınıfların ayrı ayrı iş görmesi gerekmektedir. Örneğin, bir araba objesi için motor, direksiyon, vites kutusu sınıfları oluşturulabilir. Böylece, her bir sınıf kendi işlevlerini yürütür ve değişiklik yapılması durumunda diğer sınıflara etki etmez.

Ayrıca, Yüksek cohesion kullanmak sınıfın modülerliğini korumanıza yardımcı olur. Sınıfın farklı parçalarını gerektiği gibi yer değiştirebilir ve yeniden kullanabilirsiniz. Bu, sınıfın daha genel bir bakış açısıyla yaratılmasını kolaylaştırır.


Düşük Bağımlılık

Düşük bağımlılık, nesne yönelimli tasarım prensiplerinin önemli bir parçasıdır. Bu prensip, kodun bir parçasının diğer bir parçasına karşı bağımlı olmaması gerektiğini belirtir. Bu, kodun daha kolay değiştirilebilir hale gelmesini ve yeniden kullanılabilmesini sağlar.

Bağımsız bir kod tasarlamak için, her nesnenin herhangi bir diğer nesneyle mümkün olduğunca az bağımlı olması gerekir. Bunu yapmanın bir yolu, nesnelerin aralarındaki bağımlılıkları azaltmak ve aralarındaki iletişimi bir arayüz üzerinden yapmaktır.

Örneğin, bir uygulamanız varsa ve bir veri kaynağına bağlıysanız, bu veri kaynağının değişmesi durumunda kodunuzun tümüyle yeniden yazılması gerekebilir. Bunun yerine, bir arayüz kullanarak bu veri kaynağına olan bağımlılığı azaltabilir ve daha sonra arayüz üzerinden iletişim kurabilirsiniz. Bu sayede veri kaynağı değişse bile kodunuzu yeniden yazmak zorunda kalmazsınız.

Bağımlılıkların tersine çevrilmesi prensibi, kodunuzun daha esnek ve yeniden kullanılabilir hale gelmesine yardımcı olur. Kodunuzda bu prensibi kullanmak, daha az hata yapmanıza ve daha az zaman harcamanıza da yardımcı olacaktır.


OCP: Açık Kapalı Prensibi

OCP, Açık Kapalı Prensibi anlamına gelir. Bu prensip şunu ifade eder: Bir modül değişiklikler için açık, değişikliğe kapalı olmalıdır. Bu prensip, yazılım sistemlerindeki modüllerin birbirlerinden ne kadar bağımsız olduğunu ve birbirlerinin kodlarına ne kadar müdahale etmeleri gerektiğini belirler.

Bu prensip, uyarlanabilir modüler kod yazmanın önemini vurgulamaktadır. Kodun belirli bir modül veya fonksiyon üzerinde bir değişiklik yapılması durumunda, diğer modüllere ve sistemin diğer bölümlerine minimal etki etmesi gerekmektedir.

Bu prensibi uygulamak için, kodların modüler temele dayanması gerekmektedir. Yani, her bir modülün kendi işlevselliğini yerine getiren bölümleri bulunmalıdır. Bu bölümler, gerektiğinde uyarlanabilir olmalıdır. Ayrıca, modüllerin aralarındaki bağlantıların azaltılması ve gereksiz kod tekrarının önlenmesi için bir yapılandırma kullanılmalıdır.

Bir diğer önemli nokta da, kodun geliştirilmesi sırasında tüm olası senaryolara göre yazılması yerine, mevcut gereksinimlere uygun olarak yazılmasıdır. Yazılımın genişletilebilirliğini sağlamak için, yeni gereksinimler geldiğinde sadece ilgili modüllere değişiklik yapılması gerekmektedir.

Özetlemek gerekirse, Açık Kapalı Prensibi (OCP) uyarlanabilir, modüler ve esnek kod yazmak için önemli bir prensiptir. Bu prensibi uygulayarak, yazılımlarınızın genişletilebilirliği, bakımı ve toplam maliyeti önemli ölçüde iyileştirilebilir.


LSP: Liskov'un Yerine Koyma Prensibi

LSP, yani Liskov'un Yerine Koyma Prensibi, nesne yönelimli tasarımda oldukça önemli bir yere sahiptir. Bu prensip, bir alt sınıfın üst sınıf tarafından tanımlanan davranışları yerine getirdiği sürece, alt sınıfın da üst sınıf ile yer değiştirebilir olması gerektiğini savunur. Yani kısacası, bir üst sınıftan türetilmiş alt sınıfların, üst sınıfın yerine kullanılabilmeli ve aynı davranışları sergileyebilmelidir.

Bu prensibin amacı, bir alt sınıfın, üst sınıfın yerine geçtiği durumlarda, programın çalışmasını engelleyecek hataların oluşmamasını sağlamaktır. LSP prensibi, programların daha esnek ve kolayca genişletilebilir hale gelmesine de olanak tanır. Özellikle obje odaklı yazılım mimarilerinde kullanılan LSP prensibi, yazılım sistemlerinin daha sağlam ve yüksek kaliteli olmasını sağlar.

  • Liskov'un yerine koyma prensibinin önemli noktaları şunlardır:
  • Kodun daha anlaşılır hale gelmesini sağlar.
  • Programlama hatalarını minimuma indirir.
  • Kodların yeniden kullanılabilirliğini artırır.
  • Kodların daha kolay bir şekilde sürdürülebilir olmasını sağlar.

Liskov'un yerine koyma prensibi, programlama dilinden bağımsız olarak her obje odaklı yazılım mimarisinde kullanılabilir. Bu prensibi anlamak, nesne yönelimli tasarımın önemli bir parçasını anlamak anlamına da gelir.


ISP: Arayüz Ayrımı Prensibi

ISP ya da Arayüz Ayrımı Prensibi, OOD'nin önemli prensiplerinden biridir. Bu prensip, bir arayüzün yalnızca ihtiyaç duyulan işlevleri içermesi gerektiğine işaret eder. Yani, bir arayüzde kullanılmayan işlevlerin olmaması gerekir. Bu sayede, hem kodun esnekliği artar, hem de gereksiz işlevlerin olmaması kodun anlaşılmasını kolaylaştırır.

Bir arayüz oluştururken, tek bir görev ya da işlev için tasarlanması önemlidir. Ayrıca, soyut bir yapıda olması ve bağımlılıkları sınırlaması da gereklidir. Bu sayede, kodun modülerliği artar ve değişiklik yapılması gereken durumlarda bu değişiklikler kolayca yapılabilir.

Arayüzler, bir sınıf içinde bulunan işlevlerin birleştirilmesiyle oluşturulabilir. Bu sayede, benzer işlevleri olan sınıfların kod tekrarı yapmadan bu işlemleri tek bir arayüz altında toplamaları mümkündür. Arayüzler, OOP'nin diğer prensipleriyle birlikte kullanılarak, kodun daha anlaşılır ve modüler olmasını sağlar. Ayrıca, arayüzler sayesinde, bir uygulamanın farklı bileşenleri birbirinden bağımsız çalışabilir.


DIP: Bağımlılıkların Tersine Çevrilmesi

DIP, nesne yönelimli tasarım prensiplerinin en önemlilerinden biridir. Bağımlılıkların tersine çevrilmesi prensibi, yüksek tutarlılık ve uyumluluk sağlayan bir yapı sunar. Bu prensip, kodun hem test edilebilir hem de değiştirilebilir olmasını sağlar.

DIP'ye göre, sistemin yüksek seviye modülleri, düşük seviye modüllerine bağımlı olmamalıdır. Bunun yerine, her iki seviye modül de soyutlamalara bağımlı olmalıdır. Bu, yüksek seviye modüllerin düşük seviye modüllerdeki değişikliklerden etkilenmemesini sağlar. Bununla birlikte, düşük seviye modüllerin, üst seviye modüllere uygun soyutlamaları sağlaması gerekmektedir.

DIP prensibinin uygulanması, yazılım geliştirme sürecinde oldukça önemlidir. DIP, nesne yönelimli kodun daha kolay okunabilir ve yönetilebilir olmasını sağlar. Ayrıca, düzgün uygulandığında, DIP prensibi, sistemin daha iyi ölçeklenebilir olmasını sağlar.

Tablo olarak daha net anlatabiliriz:

Daha öncesi DIP sonrası
Yüksek seviye modüller, düşük seviye modüllere doğrudan bağımlıdır Soyutlamalara bağımlılık
Düşük seviye modül değişimleri, üst seviye modülleri etkiler Üst seviye modüller, değişikliklerden etkilenmez
Bir değişiklik, tüm sistemin etkilenmesine neden olabilir Mutasyon sadece düşük seviye modüllerde etkili olabilir

DIP prensibinin önemi, bir yazılımın büyüklüğü ve karmaşıklığı arttıkça daha da artar. Çok sayıda modül ve alt sistem içeren büyük bir yazılım projesinde, düşük seviye modüllerin üst seviye modüllere bağımlı olması, kodun okunaklılığını azaltarak karışıklık ve hatalara neden olabilir. Bu nedenle, DIP prensibinin doğru şekilde anlaşılması ve uygulanması, nesne yönelimli yazılım geliştirme süreci için oldukça önemlidir.


Nesne Yönelimli Tasarım Desenleri

Nesne Yönelimli Tasarım (OOP), yazılım tasarımını daha esnek ve organizeli hale getiren bir yapıdır. OOP'nin temelinde, nesnelerin birbirleriyle etkileşim halinde olması yer alır. Bu sayede, daha büyük projelerde bile sınıfların bağımsız olarak tasarlanıp geliştirilmesi mümkün olur. OOP'nin en iyi uygulamaları arasında, Nesne Yönelimli Tasarım Desenleri (OOD) yer alır.

OOD desenleri, sınıfların doğru tasarımıyla ilgili sorunları çözmeye, daha uyumlu ve yeniden kullanılabilir bir yapıda yazılım oluşturmaya yardımcı olur. En sık kullanılan OOD desenleri arasında, Creational Patterns, Structural Patterns ve Behavioral Patterns yer alır.

Creational Patterns, nesnelerin nasıl oluşturulacağına yönelik desenlerdir. Bu desenler, nesne oluşturma işlemlerindeki kaynak kullanımını minimize etmeye ve yinelemeyi azaltmaya yardımcı olur. Singleton deseni, Factory Method deseni ve Abstract Factory deseni, Creational Patterns'in en sık kullanılan desenlerindendir.

Structural Patterns, sınıfların nasıl yapılandırılacağına yönelik desenlerdir. Bu desenler, özellikle benzer ama birbirinden farklı sınıfların arasındaki uyumluluğu artırmaya yardımcı olur. Adapter deseni, Bridge deseni ve Composite deseni Structural Patterns'in en sık kullanılan desenleridir.

Behavioral Patterns, nesnelerin nasıl birbirleriyle etkileşebileceğine yönelik desenlerdir. Bu desenler, sınıflar arasındaki etkileşimi yönetmek ve birbirinden bağımsız olan nesnelerin daha uyumlu çalışmasını sağlamak için kullanılır. Observer deseni, Strategy deseni ve State deseni Behavioral Patterns'in en sık kullanılan desenlerindendir.


Creational Patterns

Creational desenleri, nesne oluşturma işlemini ele alan tasarım desenleridir. Bu desenler, obje oluşturma işlemi sırasında yapılabilecek değişiklikleri azaltmak ve daha esnek, genişletilebilir kod yazmak için kullanılır. Bu desenlerin özellikleri ve kullanım durumları aşağıda belirtilmiştir:

  • Singleton Deseni: Tek bir nesne oluşturma işlemi yapılan durumlarda kullanılır. Bu desen, sınıfın sadece bir örneğinin oluşturulmasını sağlar ve herhangi bir yerde bu örneğe erişim sağlamak mümkündür.
  • Factory Method Deseni: Nesne oluşturma işleminin alt sınıflara bırakılması için kullanılır. Bu desen sayesinde, alt sınıfların nesne oluşturma işlemini farklı şekillerde yapabilmesi mümkün olur.

Creational desenler, nesne oluşturma işlemi sırasında karşılaşılan problemlere çözüm sunan tasarım desenleridir. Bu desenler, kodun daha esnek ve uyarlanabilir olmasını sağlayarak, yazılım geliştirme sürecini kolaylaştırırlar. Yine de creational desenlerin kullanımı, her durumda doğru olmayabilir ve uygulanan desenin probleme uygunluğu dikkate alınmalıdır.


Singleton Deseni

Singleton deseni, nesne yönelimli programlama (OOP) prensiplerinden biridir. Bu prensibe göre, belirli bir sınıftan yalnızca tek bir örnek nesne üretilir ve tüm uygulamada bu tek örneğe erişilir. Bu tekil örnekle, uygulama içinde tutulan verilerin konsolide edilmesi amaçlanır.

Singleton deseniyle, uygulamada birden fazla örnek nesne yerine bir tek örnek nesne kullanılır. Bu sayede gereksiz bellek kullanımı ve performans kaybı engellenerek, kodun daha verimli hale getirilmesi sağlanır. Özellikle çoklu kullanıcı ve işlemci sistemlerinde singleton deseni daha fazla kullanılır.

Bir örnek olarak, bir uygulamada tüm kullanıcıların veri doğrulama işlemlerinin tek bir noktada çözülmesi gerektiğinde singleton deseni kullanılabilir. Böylece, tek bir nesneye erişilerek bu işlem yapılabilir ve böylece veri doğrulama işlemleri daha tutarlı hale getirilir.

Singleton deseni genellikle aşağıdaki gibi uygulanır:

  • Öncelikle, sınıfın constructor metodu özel (private) olarak tanımlanır ve dışarıdan erişilemez hale getirilir. Bu sayede, sınıfın kontrolsüz bir şekilde örneklenmesi önlenir.
  • Ardından, sınıfın tek örneğini tutacak bir değişken tanımlanır ve bu değişkene ancak sınıfın içinde erişilmesi sağlanır.
  • Son olarak, sınıfın tek örneği için bir static metot yazılır ve bu metotla sınıfın tek örneğine erişim sağlanır. Bu sayede, sınıfın tek örneği dışarıdan kod tarafından oluşturulamaz, yalnızca sınıfın içindeki static metotla erişim mümkün olur.

Singleton deseni, uygulama geliştirirken aşırı ölçüde kullanılmamalıdır. Bu prensip, yalnızca belirli durumlarda gereklidir ve doğru şekilde uygulanmalıdır. Ayrıca, singleton deseninin doğru uygulanması için sınıfın thread-safe (çoklu işlemci kullanılan uygulamalarda, aynı anda birden fazla işlem yapan bir program) olarak tasarlanması da önemlidir.


Factory Method Deseni

Factory Method Deseni, nesne yönelimli tasarım prensiplerinden biridir ve bir sınıfın bir nesneyi üretmekle sorumlu olduğu yaratıcı bir tasarım desenidir. Bu desen, bir nesne oluşturma işlemini alt sınıflarda gerçekleştirme seçeneği sunar ve böylece ana sınıfın alt sınıflarla uyumlu hale getirilmesine imkan sağlar.

Bu desenin farklı kullanım durumları vardır. Örneğin, bir sınıfta belirli bir şekilde tek bir nesne örneği yaratılmak isteniyorsa Singleton deseni yerine Factory Method deseni kullanılabilir. Ayrıca, nesne yaratma sürecinin alt sınıflar tarafından özelleştirilmesi gereken durumlarda da bu desen kullanılabilir.

Bir Factory Method örneği, bir cep telefonu fabrikasını düşünebiliriz. Ana sınıf, cep telefonu nesnelerini yaratan bir metod içerecektir. Bu metot, çağrıldığında üretilen cep telefonunun tipine göre uygun alt sınıfın kullanılmasına imkan sağlar. Örneğin, Apple cep telefonları için üretilen bir Factory Method, iPhone için uygun alt sınıfı kullanacak ve Samsung için üretilen bir Factory Method, Galaxy telefonları için uygun alt sınıfı kullanacaktır.

Factory Method Deseni, kod tekrarını önlemeye, alt sınıfların uyumluluğunu artırmaya ve kodun özelleştirilmesine olanak sağlayarak tasarım ve geliştirme sürecini kolaylaştırır.


Structural Patterns

Structural Patterns:
Yapısal desenler, nesne yönelimli sistemlerde farklı nesneler arasındaki ilişkilerin tanımlanmasını ve düzenlenmesini sağlamaktadır. Bu desenler, bir sistemin yapısal bileşenlerini ve nesnelerin nasıl bir araya geldiğini modelleyebilir. Bu desenler, kodun kolayca anlaşılması, yeniden kullanılabilmesi ve bakımının yapılması için yardımcı olur.

Bu desen, iki farklı yapı arasında bir köprü oluşturmak için kullanılır. Adapter deseni, mevcut bir arayüzü, başka bir arayüz aracılığıyla kullanılabilir hale getirir. Bu desen, bir API'nın değiştirilmesi gerektiğinde de kullanışlıdır. Adapter deseni, sistemler arasında iletişim kurarken ve bir sistemin diğer sistemlerle uyumlu olmasını istediğinde sıklıkla kullanılır.

Bu desen, bir nesnenin özelliklerini dinamik olarak değiştirmek için kullanılır. Decorator deseni, bir nesneye dinamik olarak ek özellikler eklemek istediğimizde kullanılır. Bu desen, özelliklerin istendiği gibi değiştirilmesine olanak tanır ve bütüncül bir yaklaşım sağlar. Decorator deseni, sınıfın modifiye edilmesi gerektiğinde önemli bir rol oynar, diğer desenlerle birleştirilebilir ve modüler bir yapıda kullanılabilir.

Özetle, yapısal desenler nesnelerin birleştirilmesini modellemede yardımcı olur ve kodun yeniden kullanılmasını kolaylaştırır. Adapter deseni, farklı yapılar arasında köprü görevi görürken, Decorator deseni ise nesnelere özelliklerin dinamik olarak eklenebilmesini sağlar.


Adapter Deseni

Adapter deseni, yazılımda kullanılan tasarım desenlerinden biridir. Bu desen, farklı arayüzlerin birbirleriyle uyumlu hale getirilmesine yardımcı olmak için kullanılır. Genellikle iki arayüz arasında köprü görevi görür.

Adapter deseninin kullanımı, kodun yeniden kullanılabilirliği açısından oldukça önemlidir. Ayrıca, farklı modüller arasında bağlantı sağlayarak, karmaşık yazılımların daha kolay bir şekilde geliştirilmesine yardımcı olur.

Adapter deseni, özellikle farklı sistemlerin birbirleriyle çalışabilmesi için bir arayüz sağlamak istediğiniz durumlarda kullanışlıdır. Örneğin, bir uygulamanın verilerini bir veritabanından çekmek istediğinizde, farklı veritabanı türleri arasında değişen veri yapıları ile karşılaşabilirsiniz. Bu durumda, bir Adaptör kullanarak farklı veri yapılarını birleştirerek, uygulamanızın verimli bir şekilde çalışabilmesini sağlayabilirsiniz.

Adapter deseninin yapısı, bir Adaptee (adaptör olacak sistem), bir Target (hedef arayüz) ve bir Adapter (Adaptee'nin Target arayüzüne dönüştürüldüğü yer) içerir. Bu sayede, farklı arayüzlerdeki nesnelerin birbiriyle ilişkilendirilmesi sağlanır.

Adapter deseni, yazılımın esnekliğini artırır ve kodun daha okunaklı olmasını sağlar. Ayrıca, kodu daha sade hale getirerek, bakım maliyetlerini azaltır. Bu nedenle, yazılım mühendisleri tarafından sıkça kullanılan bir desendir.


Decorator Deseni

Decorator deseni, nesne yönelimli tasarımdaki yapısal bir desendir. Bu desen, bir nesne örneğine dinamik olarak yeni işlevler veya sorumluluklar eklemek için kullanılır. Bu ek işlevler, nesnenin kendisine yapılan değişiklikler olmadan yapılır.

Decorator deseni, bir arayüzü uygulayan bir ana sınıfı (component) ve bu ana sınıfı genişleten birden çok dekoratör sınıfını (concrete decorator) içerir. Dekoratör sınıflarının görevi, ana sınıftaki nesne örneğine ek işlevler eklemektir. Bu sayede, farklı işlevleri olan birden fazla nesne tasarlanabilir.

Bu desen, özellikle GUI uygulamalarında kullanışlıdır. Örneğin, bir butonun üzerine farklı arka plan resimleri veya yazı stilleri eklemek için kullanılabilir. Ayrıca, farklı kostenya eklenerek, bir kullanıcının seçimlerine göre farklı malzemelerin birbirine eklenmesi gibi durumlarda kullanılabilir.

Decorator deseni, Open-Closed prensibinin uygulanmasına olanak tanır. Bu prensip, kodun değiştirilmeden, ancak eklemeler yapılarak genişletilebilir olmasını sağlar. Ayrıca, bir dekoratör sınıfının, diğer dekoratör sınıflarıyla da kullanılabilmesi, bu desenin kullanımını daha da yaygın hale getirir.


Behavioral Patterns

Nesne yönelimli tasarımın son aşaması, davranışsal tasarım desenlerini içerir. Davranışsal tasarım desenleri, nesneler arasındaki işbirliği ve davranış hakkında kapsamlı bilgi sağlar.

Observer Deseni: Observer deseni, bir nesnenin durumundaki değişiklikleri takip eden ve diğer nesnelerin bu değişikliklerden haberdar olmasını sağlayan bir desendir. Bu desen, tek bir nesnenin özelliklerinde bir değişiklik olduğunda diğer nesnelere haber vermeye yarar.

Strategy Deseni: Strategy deseni, farklı algoritmaların veya davranışların birbirinden bağımsız bir şekilde kullanılabilmesini sağlar. Bu desen, bir nesnenin davranışını değiştirmeden algoritma değişiklikleri yapmamıza olanak tanır.

Davranışsal desenler, nesneler arasındaki işbirliği, iletişim ve davranışlar hakkında bilgi sağlar. Bu desenler, bir yazılımın daha esnek, anlaşılır ve ölçeklenebilir olmasına yardımcı olur.


Observer Deseni

Observer deseni, nesneler arasındaki bir değişiklik durumunda otomatik olarak diğer nesnelere haber vermek için kullanılır. Bu prensip, birçok nesne arasında dinamik iletişim oluşturmak için kullanılır.

Observer deseni, birçok nesneler arasındaki ilişkiyi, bir nesnede yapılacak herhangi bir değişikliği otomatik olarak diğer nesnelere aktarmak için kullanılır. Örneğin, bir müşteri bir sipariş verirse, sipariş durumunu takip etmek için birden fazla nesne olacaktır. Sipariş durumu değişirse, birden fazla nesneye müşteriye haber vermek gerekir. Bu durumda observer deseni kullanmak uygun bir seçenektir.

Observer deseni, tek bir nesne değiştiğinde birçok nesnenin uygun şekilde güncellenmesini sağlar. Bu, nesneler arasındaki sıkı bağımlılığı ortadan kaldırır ve kodun daha esnek hale gelmesine izin verir. Örneğin, bir kişinin veritabanındaki bilgileri değişirse, birden fazla nesneye bu değişiklikleri manuel olarak aktarmak yerine, observer deseni uygulanarak tüm nesnelere otomatik olarak haber verilebilir.

Observer deseni, yazılımda sık kullanılan bir tasarım desenidir. Özellikle kullanıcı arayüzü, e-ticaret siteleri ve mobil uygulamalar gibi birçok farklı alanda kullanılmaktadır. Bu desen, nesneler arasındaki iletişim ve etkileşim konusunda özel bir gereksinim olduğunda özellikle faydalıdır.

Observer Deseni Faydaları Observer Deseni Dezavantajları
  • Flexibility
  • Low coupling
  • Scalability
  • Easy to maintain
  • Additional overhead to notify observers
  • May cause performance issues with a large number of observers

Strategy Deseni

Strategy deseni, bir nesnenin birden çok davranışına sahip olmasını ve bu davranışların doğru zamanda seçilip kullanılmasını sağlar. Bu desen, bir interfacenin birden fazla uygulanabileceği çoklu kalıtımın yerine kullanılabilir.

Bu desen, kodun daha açık ve okunaklı hale gelmesini sağlar ve uygulamada değişiklik yapılması gerektiğinde değiştirilmesi kolay bir şekilde tasarlanır. Ayrıca, kodun test edilmesini kolaylaştırır.

Bir örnek olarak, bir oyun programı düşünelim. Bu programda farklı stratejiler uygulayarak farklı sonuçlar elde etmek mümkündür. Örneğin, bir tankın ilerleme stratejisi, bir mümkün düşman saldırısı stratejisi veya bir jet uçağının hareket stratejisi olabilir. Bu senaryoda, her strateji için ayrı sınıflar oluşturmak yerine Strategy deseni kullanılabilir.

Strategy deseni ayrıca, takım çalışması gerektiren projelerde de oldukça kullanışlıdır. Bir proje yöneticisi, farklı üyelerin farklı stratejiler uygulamasını ve bu stratejilerin en verimli şekilde kullanılmasını sağlayabilir.

Özetlemek gerekirse, Strategy deseni bir nesnenin farklı davranışlarını temsil etmek için kullanılır ve uygulama tasarımının daha esnek ve okunaklı hale gelmesine yardımcı olur.