İçeriğe geç →

C# Strategy Pattern Kullanımı

Tasarım desenleri makale serimize yine Behavioral tasarım kalıpları grubunda yer alan Strategy tasarım deseni ile devam edeceğiz. Açıkçası en sevdiğim GOF(Gang of Four) desenlerinden birisidir de diyebilirim. 🙂

Evet haydi bakalım neymiş bu Strategy?

İsminden de anlaşılacağı üzere bir işi yapabilecek birden fazla algoritmamız var ise orada hemen Strategy tasarım deseni ben buradayım diye bağırır. 🙂 En sık kullanılan tasarım deseni olduğunu da belirtmek isterim.

Neden kullanmalıyız?, sorusuna baktığımızda ise size kısaca şunu diyebilirim:

Yapılması istenilen bir işimiz var ve bu işi birden farklı yollarla yapma ihtiyacımız var. Bu gibi durumlarda var olan işi ilgili sınıfı sürekli refactor ederek if-else blokları ile yapmak yerine, yeni bir sınıf daha ekleyerek istenilen durumda ilgili işi ilgili sınıfta yapmamıza olanak sağlar. Böylece var olan sınıfımız üzerinde değişiklik yapmadan sistemimizi geliştirmiş olacağız. Burada en önemli tasarım prensiplerinden birisini olan Open-Closed prensibi söz konusudur.

İlgili desenimizin UML Diyagramına baktığımızda:

StrategyDiagramDiyagrama göz attığımızda Context ile Strategy sıfını arasında aggregation(bu tür bir ilişkide ilgili nesnelerin yaşam döngüleri birbirlerinden ayrıdır) türünde bir ilişki olduğunu görmekteyiz.

Strategy: Bir arayüz(Interface) tasarlayarak ortak olan tüm algoritmalarımızı burada toplarız.
ConcreteStrategy: Ilgili algoritmayı gerçekleyen gerçek sınıfımız.

Lafı fazla uzatmadan terminolojiyi bir kenara bırakarak hemen bir real-world örneği yapalım:

Örneğimizde bir e-ticaret sitesindeki ödeme kütüphanesini ele alalım. Birden fazla yöntemle ve banka ile çalışıyor olabiliriz bu sistemde. İster banka transferi ile ister mail order yöntemi ile veya sanal pos yöntemi ile ödemeyi çekiyor olabiliriz.

Öncelikle yukarıda bahsettiğimiz gibi ortak olan algoritmamız örneğimiz gereği ile MakePayment metotu olsun ve ilgili arayüzümüzü tasarlamaya geçelim.

İlgili arayüzü tasarladığımıza ve MakePayment metotunu tanımladığımıza göre gerçekleyecek olan ilgili ConcreteStrategy‘lerimizi oluşturmaya başlayalım.

Mail order ödeme yöntemini sistemimize uyarladık ve ilgili MakePayment metotunu bir mesaj yazdırarak doldurduk. Sistem her zaman gelişime açık olmalı demiştik ya? Birde şirketler sürekli yeni bir şeyler isterler malum 🙂 Müşterimiz bizden bu seferde banka transferi yöntemi ile ödeme tipinin de entegre edilmesini istedi.

İşte bu kadar basit. IPayment arayüzünü implemente ederek sistemimizi genişletmiş olduk. Evet durmak yok! Bu seferde sanal pos yöntemi ile ödeme çekilmesini istediler bizden, hazırlıklı olduğumuz için hemen yine işe koyuluyoruz. 🙂

İşte bu da bu kadar basit. 🙂 İyi güzel hoş, gerçekleyen sınıflarımızı oluşturduk istekler doğrultusunda ama ben bunu nasıl kullanacağım? Huh?

Hemen Context‘imizi yani örneğimiz gereği PaymentOperation sınıfını hazırlayalım. Bir nevi ilgili ödeme işlemini sarmalayıp developerlara daha basic bir kullanım sunan wrapper sınıfımız.

Sarmalayıcı sınıfıda constructor injetion yaparak hazırladığımıza göre hemen örneğimizin kullanımına bir göz atalım:

Basit tutmaya çalışarak ve real-world örneği vererek daha anlaşılır bi hale gelmesini istedim. Bir sonraki makalemde görüşmek dileğiyle. 🙂

 

Bu makale toplam (2484) kez okunmuştur.

17
0



Kategori: Tasarım Kalıpları (Design Patterns)

6 Yorum

  1. Enver Yasin Erdoğdu Enver Yasin Erdoğdu

    Eline, ağzına sağlık Gökhan’ım. Kanka Factory pattern’i anlatırken, Strategy pattern’le aralarındaki farkı anlatırsan, bide benim araştırdığım bazı makalelerde beraber kullanılmaları tavsiye ediliyor, o konuda da yazarsan on numara olur.

  2. Ankara Ankara

    Factory pattern bu

  3. Caner Caner

    E bu factory pattern ?

    • Merhaba, bu iki pattern birbirine benzemektedir. Factory sadece object creation ile ilgilenirken, Strategy ise farklı algoritmalarla işlem yapabilmek için bir mekanizma sağlamaktadır. Factory’yi farklı strategy’ler create edebilmek için de kullanabiliriz.

  4. Mehmet Mehmet

    Merhaba,

    Yine if – else yazmış olduk. Buradaki amaç if else yazmadan uygulamada farklı kodları çalıştırmak değil mi ? Burada sanki kodları class’lar içine alarak daha düzenlemiş olduk. Open – Close prensibi nerede kullanılmış oldu 🙂

    • Merhaba evet haklısınız, if-else i burada kullandığımız kısım, oluşturulan “PaymentOperation” ın kullanıldığı noktada. Dilerseniz o noktayı da küçük bir reflection ile generic hale getirebilmek mümkündür. 🙂 Veya “PaymentOperation” ı herhangi bir DI container’ı ile de inject edebilirsiniz farklı senaryolar karşısında. Tamamen use-case’e göre değişiklik gösterebilecek bir durum açıkcası.

Bir cevap yazın

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

*