Python gibi dinamik dillerde gereksiz tasarım desenleri var mı?


98

GoF tarafından tasarım deseni kitabını okumaya başladım. Bazı modeller sadece küçük kavramsal farklılıklar ile çok benzer görünüyor.

Python gibi dinamik bir dilde bazılarının gereksiz olduğunu düşünüyor musunuz (örneğin, dinamik bir özellik ile değiştirildikleri için)?


1
İlginç bir soru, çünkü dil seçiminin kod yapılarının yerine etkili bir şekilde geçebileceğini ima ediyor.
joshin4colours

3
Bir cevap değil, ama alakalı - GoF tasarım kalıplarının, belirli kalıplarda olduğu gibi, bunlardan damıtılabilecek bazı genel ilkeler ile ilgili olduğunu düşündüm. Bir kalıp fikrini kastetmiyorum (kesinlikle önemli olsa da), ancak daha saf OOP ilkelerini ihlal eden belirli şekillerde sınıfları kullanma izni. Örneğin, “biçimin” açıkça açıkça “kendini çizmediği” veya en azından işin bir yönünü başka bir nesneye devrettiği birçok desen vardır. OOP'yi destekleyen herhangi bir dilde dersin önemli olduğunu düşünüyorum.
Steve314

Çok ilginç bir soru. Keşke + 1 yerine +5 yapabilseydim.
MathAttack

1
En Bakış videoları Are Tasarım Patterns Eksik Dil Özellikleri ve Tasarım Kalıpları Dil Özellikleri Eksik c2 de bitti. 'Dinamik dil' meselesi bile değil. En basit örnek python, perl (ve hatta Java - dinamik değil) açısından önemsiz olan yineleyici modelidir.

Yanıtlar:


92

Peter Norvig, GOF kitabında bulunan 23 tasarım deseninden 16'sının dinamik dillerde görünmez veya daha basit olduğunu gösteriyor (Lisp ve Dylan'a odaklanıyor).

Python'dan bahsettiğinizden beri, Alex Martelli'nin konuyla ilgili güzel bir sunum var . Ayrıca Python ile ilgili olarak, deyimsel Python'da altı tasarım modelini gösteren hoş bir blog yazısı var .

Ayrıca Python'daki en yaygın tasarım modellerinin uygulamaları (diğer insanlar tarafından) ile github deposunu saklıyorum .


Harika! Bu cevapta bir nokta olurdu :) Herkesin açıkça soruyu kavramasını diledim.
Gerenuk

2
Norvig'e göre, 16 kişiden 2'si (Tercüman ve Tekrarlayıcı) makrolardan dolayı (Python'un sahip olmadığı) “görünmez ya da daha basit”.
mjs

1
tüm bu kalıpların gerekmediği açık değil, çünkü lisp dinamik değil, güçlü bir fonksiyonel dil olmak gibi diğer özelliklerden dolayı
jk.

@mjs Yineleyiciler Python'un yerleşik bir özelliğidir.
sakisk

1
Bu harika cevap, anlamsız bağlantı başlıklarının gösterdiği , sunumunu ve deposunu göstermesiyle biraz da olsa geliştirilebilir - burada çok daha
Wolf

59

Tasarım deseni gerekmez. Herhangi bir dilde

Tasarım kalıplarını okuyan ve daha sonra onları her yerde kullanmaları gerektiğini düşünen insanlar tarafından yazılmış bir çok kodla karşılaşmaya meyilliyim. Sonuç olarak, gerçek kodun tonlarca arabirim, sarmalayıcı ve katman altına gömülmesi ve okunması oldukça zor olmasıdır. Bu tasarım desenlerine yanlış bir yaklaşım.

Tasarım kalıpları mevcuttur, böylece bir sorunla karşılaştığınızda kullanabileceğiniz kullanışlı deyimler repertuarına sahip olursunuz. Ancak, sorunu tanımlayabilmeniz için asla herhangi bir desen uygulamamalısınız. Basit Tutun Aptal , daima üstün yönetim ilkesi olmalıdır.

Aynı zamanda, tasarım kalıplarını, yazılacak belirli boyler kodundan ziyade problem hakkında düşünmek için bir kavram olarak düşünmeye yardımcı olur. Ve Java'nın ücretsiz işlevlerden ve kendilerine sahip olan diğer pek çok dilde kullandığınız standart işlev nesnelerinden (Python, C #, C ++ vb.) Kullandığı Java için geçici bir çözüm olarak.

Bir ziyaretçi kalıbım olduğunu söyleyebilirim, ancak birinci sınıf işlevlere sahip herhangi bir dilde bu sadece bir işlevi alan bir işlev olacaktır. Fabrika sınıfı yerine genellikle fabrika işlevine sahibim. Bir arayüze sahip olduğumu söyleyebilirim, ancak daha sonra yorumlarla işaretlenmiş birkaç yöntem var, çünkü başka bir uygulama olmazdı (elbette python'da bir arayüz her zaman sadece yorumdur, çünkü ördek tiplidir). Kalıbı kullanmak gibi hala koddan bahsediyorum, çünkü düşünmek için yararlı bir yol, ancak gerçekten ihtiyacım olana kadar her şeyi yazmayın.

Öyleyse tüm kalıpları kavram olarak öğren . Ve özel uygulamaları unutun. Uygulama değişiyor ve gerçek dünyada, hatta sadece Java'da bile değişmeli.


28
Açılış konuşmanız aşırı derecede basitleştiricidir. Modellerin maliyetlerinin olduğu doğrudur, bu yüzden sadece uğruna, kör kullanılmamalıdır. Ancak doğru yerde, çok yardımcı olabilirler. Ve evet, bunlar dile özgüdür - bazı modeller bazı dillerde gerekli değildir çünkü dilin kendisi daha iyi bir yaklaşımı desteklemektedir. Ancak bu açılış iddianızdan hala oldukça uzak.
Péter Török

2
Btw Ziyaretçi, tamamen üst düzey işlevlerle değiştirilmemiştir - çifte gönderimi yerel olarak desteklemeyen bir dilde (C # ve C ++ gibi) uygulamak bir çözümdür. (Ve gerçekten çok idareli kullanılması gerektiğini -. Ben kullanım IMHO Kendimi o kadar hiç kullanılmamış olması haklı çok zor en gizli ve pahalı düzenlerin biri dikkate şu ana)
Péter Török

14
Asla bir şablona ihtiyacın yok . İhtiyacın olan bir sorunu çözmek . Herhangi bir model bilmiyorsanız, hala çözebilirsiniz, daha fazla düşünmeye ihtiyaç duyar ve bazı modellerle eşleşen veya çözmeyen bir çözüm bulabilirsiniz. Kalıpları bilmek sadece kolaylaştırır.
Jan Hudec

3
@Gerenuk: Evet, ama mesele şu ki, desenler dile özgü değil, onlar sizin için. Python'da genellikle bazı modellerin çok daha kolay ve farklı araçlar kullanılarak gerçekleştirildiğini görüyorsunuz, ancak aynı konsept genellikle var.
Jan Hudec

4
@ PéterTörök: Ziyaretçi hiçbir şeyle değiştirilmez. Mesele aynı kavramın farklı durumlarda farklı araçlar kullanılarak uygulanabileceği, ancak yine de aynı kalıp olduğunu düşünüyorum.
Jan Hudec

13

Python gibi ördek tipli bir dilde soyut bir fabrika düzeni gerekli değildir, çünkü dilin içine yerleştirilmiştir.


10
peki, hala farklı fabrikalara ihtiyacın var. Arayüz tanımına ihtiyacınız yok.
Stefano Borini

1
Eğer bir sınıfınız varsa, zaten bir fabrikanız var. Sınıflar birinci sınıf nesnelerdir ve her yere yayılabilir ve bir nesneyi (Java'nın aksine) oluşturmak için çağrılabilir. Başka bir şey yaratmanıza gerek yok. Varsayılan yapıcı olmayan bir şey istiyorsanız, yapıcıyı bir şekilde saran bir tür lambda / callable oluşturun.
spookylukey

13

Akla gelen tek Singleton deseni.

Python sizi her şey için sınıfları kullanmaya zorlamadığından , bunun yerine sadece global bir veri yapısını kullanabilirsiniz. Yani küresel veri yapısı olabilir bir örneği tarafından yönetilecektir, ancak sadece ithalat örneği oluşturun ve öyle bırakabilir, bu sınıfın örnekleme kontrol etmek gerekmez.

Çoğunlukla, python içindeki Singletons bir modül ile değiştirilir. Python'daki modüller doğası gereği Singletons; python yorumlayıcısı bunları yalnızca bir kez ve bir kez oluşturur.

Python'da kullandığım Tasarım Patikalarındaki diğer tüm desenleri bir anda veya diğerinde bulabilirsiniz ve bunların örneklerini Python standart kütüphanesinde ve Python'da bulabilirsiniz.


2
Bu aslında bugünlerde bir anti-patern değil mi?
Den

16
Singleton bir antipattern . Bütün dillerde İlişkili olmayan birkaç problemi çözmek için yaratılmıştır ve her ikisi için de iyi bir eşleşme değildir (Java'nın bile, sınıf başına bir kez varolan statik üyeleri olduğunu, bunun için bir örneğe ihtiyacınız olmadığını unutmayın).
Jan Hudec

1
Ve Python'da çözecek bir problem olmadığından asla rahatsız etmedik.
Martijn Pieters

1
"Python sizi her şey için nesne kullanmaya zorlamıyor" Doğru değil. Java'da olduğu kadar iğrenç değil, ama yine de Python'da her şey bir nesnedir. Hatta modül bile bir nesnedir.
vartec

3
@Darthfett: Nasıl lençalıştığını çok iyi biliyorum ; Guido burada açık bir seçim yaptı . Demek istediğim Python'un saf bir OOP dili olmadığını göstermek; pragmatik bir dildir. Bu şekilde seviyorum.
Martijn Pieters

8

Tasarım kalıpları dil için değil programcı içindir. Programcılar, eldeki problemi anlamalarına yardımcı olan kalıpları kullanma eğilimindedir. Hiçbir tasarım deseni kesinlikle gerekli değildir, ancak ne yapmaya çalıştığınızı basitleştirmek için faydalı olabilir.

Python ve özellikle ördek yazarak, pek çok ortak kalıp ve uygulamanın etrafında bir son sağlar ve bazı kalıpların (gizlilik, değişmezlik, vb.) Getirdiği kısıtlamaların çoğu, yalnızca programcının bunları kırmamayacağını kabul ettiği ölçüde olur. . Ama yine de, onlar do sürece programcı boyunca oynar olarak çalışıyorum. Bir kapı, hayali duvarlarla çerçevelenmiş olsa bile, hala bir kapıdır.

Python bir "çoklu paradigma" dili olarak kabul edilir; İstediğin desenleri kullanabilirsin. Bu kasıtlı. Tamamen gereksiz ve biraz yapay olmalarına rağmen, örneğin karmaşık sınıf hiyerarşileri sağlar. Ancak bazı insanlar için bu soyutlama faydalıdır. Sorun gerektirdiği için değil, programcının gerektirdiği için. Al işte ozaman, buyur.


Bu kesinlikle ilginç. Özellikle hangi kalıpları unutabileceğinizi kastediyorsunuz, çünkü Python'da daha iyi yollar var?
Gerenuk

4

Orijinal "Tasarım Desenleri" kitabı, C ++ ve Smalltalk gibi zorunlu, nesne yönelimli dillerde yararlı olan bazı ortak deyimleri belgelemiş ve adlandırmıştır. Ancak Smalltalk dinamik olarak yazılmış bir dildir, bu yüzden kesinlikle dinamik olma meselesi olamaz.

Bununla birlikte, sorunuzun cevabı hala "evet" dir: bu tasarım modellerinden bazıları, dinamik olarak yazılmış modern dillerle ilgisiz olacaktır. Daha genel olarak orada olacak farklı özellikle farklı farklı dillerde tasarım örüntüleri türlü dillerinin.

Tekrarlamak gerekirse: bir "tasarım deseni" sadece bir programlama tabirinin adıdır: Sık karşılaşılan bir problemin ortak çözümü. Farklı diller farklı deyimler gerektirir, çünkü bir dilin sorunu ne diğeri için önemsiz olabilir. Bu anlamda, tasarım desenleri, başvurdukları dillerdeki zayıflıkları işaret etme eğilimindedir.

Dolayısıyla, modern dinamik dilleri (veya Lisp gibi eski dilleri) daha güçlü kılan ve bu klasik tasarım modellerinin bazılarını alakasız kılan diğer özellikleri arayabilirsiniz.


1

Tasarım kalıpları, belirli problemleri çözme yollarıdır. Bir sorunla karşılaşılmazsa, çözme şeklinin bir faydası olmaz.

İnsanlar, projenizde tasarım kalıplarına sahip olmanın en iyi yoluysa, tasarım kalıplarını her yere adapte etmeye çalışıyorlar. Etrafta başka bir yol var. Fabrika düzeninde çözülebilecek bir problemle mi karşılaştınız? Güzel. Uyarla. Kodunuza bakmayın ve bir singleton (veya fabrika veya cephe ya da her neyse ...) uygulamak için doğru yeri bulmaya çalışmayın.

Belki de Python'un Java ve .NET kullanıcıları için mevcut olmayan kendi tasarım desenleri vardır (bu dillerin doğası gereği)?


1

Kalıpların daima dile bağlı olduğunu söyleyebilirim. Çoğu python deseninin GoF'da tanımlananlara benzemesi, Python'un OOP'undan kaynaklanıyor, OOP'un OOP'a benzemediği söyleniyor (hiçbir iki dil nesneleri tanımlamıyor ve manipülasyonları aynı şekilde% 100).

Bu yüzden bazı modellerin "olduğu gibi" uygulanamayacağından şüphe yoktur, bazıları anlamsız olabilir ve sadece Python için anlamlı olabilecek bazı modeller vardır.

Tam olarak sorunuzu geri almak için: Desenler sadece onlara ihtiyacınız varsa gereklidir . Onlara gerek yoksa bunları kullanmak zorunda değilsiniz (Jan Hudec'in dediği gibi).

Ayrıca, GoF'ta belirtilenlerden çok daha fazla kalıp var. Wikipedia diğer kalıpları gör

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.