Standart "Model View Controller" deseni ile Microsoft'un Model / View / ViewModel modeli arasında bir fark var mı?
Standart "Model View Controller" deseni ile Microsoft'un Model / View / ViewModel modeli arasında bir fark var mı?
Yanıtlar:
İki desen ASP.Net ve Silverlight / WPF geliştirmelerinde farklı şekillerde ortaya çıkar.
ASP.Net için MVVM, görünümler içindeki verileri iki yönlü bağlamak için kullanılır . Bu genellikle bir istemci tarafı uygulamasıdır (örn. Knockout.js kullanarak). MVC ise sunucu tarafındaki endişeleri ayırmanın bir yoludur .
Silverlight ve WPF için MVVM desen daha kapsayan ve edebilirsiniz görünür MVC (veya ayrı sorumlulukları içine yazılım organize diğer desenleri) için bir yedek olarak hareket etmek. Sık sık bu modelin çıktı Bir varsayım, olmasıydı ViewModel
basitçe kontrolörü yerini MVC
(sadece yerine olabilir sanki VM
için C
kısaltması ve tüm affetmiş olabilir) ...
Sorun şudur: bağımsız olarak test edilebilir * olmak ve özellikle gerektiğinde yeniden kullanılabilir olmak için, bir görünüm modelinin onu hangi görüntünün görüntülediğine dair bir fikri yoktur , ama daha da önemlisi verilerinin nereden geldiğine dair hiçbir fikri yoktur .
* Not: Uygulamada Kontrolörler, ünite testi gerektiren mantığın çoğunu ViewModel'den kaldırır. Daha sonra VM, çok az test gerektiren aptal bir kap haline gelir. VM, tasarımcı ve kodlayıcı arasında sadece bir köprü olduğu için bu iyi bir şeydir, bu yüzden basit tutulmalıdır.
MVVM'de bile, kontrolörler tipik olarak tüm işleme mantığını içerecek ve hangi görünüm modellerinin hangi görünüm modellerini kullanarak görüntüleneceğini belirleyecektir.
Şimdiye kadar gördüğümüz kadarıyla XAML düzenlemesini daha bağımsız bir görev haline getirmek için XAML kod arkasındaki kodu kaldırmak için ViewModel deseninin ana yararı . Hala uygulamalarımızın genel mantığını kontrol etmek için (gerektiği gibi) kontrolörler yaratıyoruz.
Biz de kaydetti Heykel kod-gen çerçevesi uygular MVVM ve Prism benzer bir desen VE aynı zamanda tüm kullanım-case mantığı ayırmak için kontrolörler yoğun kullanımını kolaylaştırır.
Bu konuyla ilgili olarak ne zaman ve ne zaman ekleyeceğim bir blog başlattım . Çoğu navigasyon sistemi sadece Views ve VM'leri kullandığından MVCVM'yi ortak navigasyon sistemleriyle birleştirmeyle ilgili sorunlar var, ancak daha sonraki makalelerde bu konuya değineceğim.
Bir MVCVM modeli kullanmanın ek bir yararı , uygulamanın ömrü boyunca bellekte sadece denetleyici nesnelerinin bulunması ve denetleyicilerin temel olarak kod ve küçük durum verileri (yani küçük bellek ek yükü) içermesidir. Bu, görünüm modellerinin saklanması gereken çözümlerden çok daha az bellek yoğun uygulamalar yapılmasını sağlar ve belirli mobil geliştirme türleri için idealdir (örneğin, Silverlight / Prism / MEF kullanan Windows Mobile). Bu, elbette uygulamanın türüne bağlıdır, çünkü yine de zaman zaman önbelleğe alınan VM'leri yanıt verebilmeniz için saklamanız gerekebilir.
Not: Bu yazı birçok kez düzenlendi ve sorulan dar soruyu özel olarak hedeflemedi, bu yüzden ilk kısmı şimdi de kapsayacak şekilde güncelledim. Aşağıdaki yorumlarda tartışmanın çoğu, daha geniş resim ile değil, sadece ASP.Net ile ilgilidir. Bu yazı, Silverlight, WPF ve ASP.Net'te MVVM'nin daha geniş kullanımını kapsamayı ve insanların denetleyicileri ViewModels ile değiştirmelerini engellemeyi amaçladı.
Bu kısaltmaların ne anlama geldiğini anlamanın en kolay yolunun onları bir anlığına unutmak olduğunu düşünüyorum. Bunun yerine, her biri kaynaklı yazılımları düşünün. Gerçekten erken web ve masaüstü arasındaki farka bağlı.
2000'li yılların ortalarında karmaşık bir şekilde büyüdükçe, ilk olarak 1970'lerde açıklanan MVC yazılım tasarım deseni web uygulamalarına uygulanmaya başladı. Veritabanı, HTML sayfaları ve aradaki kodu düşünün. MVC'ye ulaşmak için bunu biraz daha düzeltelim: »veritabanı« için, veritabanı artı arayüz kodunu varsayalım. »HTML sayfaları« için, HTML şablonlarının yanı sıra şablon işleme kodunu varsayalım. »Arasındaki kodlar için«, muhtemelen veritabanını etkileyen ve kesinlikle başka bir görünümün görüntülenmesine neden olan eylemlere kod eşleme kullanıcı tıklamalarını varsayalım. En azından bu karşılaştırmanın amacı bu.
Bu web öğelerinin bir özelliğini bugün olduğu gibi değil, on yıl önce olduğu gibi, JavaScript'in düşük, aşağılık bir sıkıntı olduğu zaman, gerçek programcıların yönlendirmek için iyi yaptığı: HTML sayfası aslında aptal ve pasif . Tarayıcı ince bir istemcidir, ya da isterseniz kötü bir istemcidir. Tarayıcıda istihbarat yok. Tam sayfa yeniden yükleme kuralı. »Görünüm« her seferinde yeniden oluşturulur.
Bu web yolunun, tüm öfke olmasına rağmen, masaüstüne kıyasla korkunç bir şekilde geri olduğunu hatırlayalım. Masaüstü uygulamaları şişman istemciler veya isterseniz zengin istemcilerdir. (Microsoft Word gibi bir program bile bir tür istemci, belgeler için bir istemci olarak düşünülebilir.) Onlar zeka dolu, verileri hakkında bilgi dolu müşterilerdir. Onlar durumsal. Bellekte tuttukları verileri önbelleğe alırlar. Tam sayfa yeniden yükleme gibi bir saçmalık yok.
Ve bu zengin masaüstü yolu muhtemelen ikinci kısaltmanın kaynaklandığı yer olan MVVM'dir. Harflerle aldanmayın, C'nin atlanmasıyla. Kontrolörler hala orada. Olmaları gerekiyor. Hiçbir şey kaldırılmaz. Sadece bir şey ekliyoruz: durum bilgisi, istemcide önbelleğe alınan veriler (ve bu verileri işlemek için istihbarat ile birlikte). Bu veriler, aslında istemcideki bir önbellek, artık "ViewModel« olarak adlandırılıyor. Zengin etkileşime izin veren şey budur. Ve bu kadar.
Flash, Silverlight ve en önemlisi JavaScript ile web'in MVVM'yi benimsediğini görebiliriz. Tarayıcılar artık meşru olarak ince istemciler olarak adlandırılamaz. Programlanabilirliklerine bakın. Bellek tüketimine bak. Modern web sayfalarındaki tüm Javascript etkileşimlerine bakın.
Şahsen, somut gerçeklikte neye atıfta bulunduğuna bakarak bu teori ve kısaltma işini daha kolay anlaşılır buluyorum. Soyut kavramlar, özellikle somut madde üzerinde gösterildiğinde yararlıdır, bu nedenle anlayış tam bir döngü haline gelebilir.
MVVM Model-View ViewModel , MVC, Model-View Controller'a benzer
Denetleyici bir ViewModel ile değiştirilir . ViewModel, UI katmanının altında bulunur. ViewModel, görünümün ihtiyaç duyduğu verileri ve komut nesnelerini ortaya çıkarır. Bunu, görünümün verilerini ve eylemlerini almaya giden bir kapsayıcı nesne olarak düşünebilirsiniz. ViewModel verilerini modelden alır.
Russel East , daha ayrıntılı bir şekilde tartışan bir blog yapıyor MVVM neden MVC'den farklı?
If you put ten software architects into a room and have them discuss what the Model-View-Controller pattern is, you will end up with twelve different opinions. …
Birincisi, MVVM, ekranı işlemek için XAML kullanan MVC modelinin bir ilerlemesidir. Bu makale , ikisinin bazı yönlerini özetlemektedir.
Model / View / ViewModel mimarisinin ana ithalatı, verilerin üstünde (“Model”), verilerin kavramlarını daha yakından eşleyen başka bir görsel olmayan bileşen katmanı (“ViewModel”) olduğu görülmektedir. verilerin görünümü kavramlarına (“Görünüm”). Doğrudan Model'e değil, Görünüm'ün bağlandığı ViewModel'dir.
Microsoft , burada Windows ortamında MVVM Kalıbının bir açıklamasını sağlamıştır .
İşte çok önemli bir bölüm:
Model-View-ViewModel tasarım deseninde bir uygulama üç genel bileşenden oluşur.
Model : Bu, uygulamanızın kullandığı veri modelini temsil eder. Örneğin, bir resim paylaşım uygulamasında, bu katman bir aygıtta bulunan resim kümesini ve resim kitaplığını okumak ve bu kitaplığa yazmak için kullanılan API'yi temsil edebilir.
Görünüm : Bir uygulama genellikle birden çok kullanıcı arayüzü sayfasından oluşur. Kullanıcıya gösterilen her sayfa MVVM terminolojisinde bir görünümdür. Görünüm, kullanıcının gördüklerini tanımlamak ve biçimlendirmek için kullanılan XAML kodudur. Modelden gelen veriler kullanıcıya gösterilir ve uygulamanın geçerli durumuna göre bu verileri kullanıcı arayüzüne beslemek ViewModel'in görevidir. Örneğin, bir resim paylaşım uygulamasında görünümler, kullanıcıya cihazdaki albümlerin listesini, bir albümdeki resimleri ve belki de kullanıcıya belirli bir resmi gösteren başka bir kullanıcı arayüzü olacaktır.
ViewModel : ViewModel, veri modelini veya yalnızca modeli uygulamanın arayüzüne veya görünümlerine bağlar. Modelden verilerin yönetileceği mantığı içerir ve verileri XAML kullanıcı arayüzünün veya görünümlerinin bağlanabileceği bir dizi özellik olarak gösterir. Örneğin, bir resim paylaşım uygulamasında, ViewModel bir albüm listesi ve her albüm için bir resim listesi gösterir. Kullanıcı arayüzü, resimlerin nereden geldiği ve nasıl alındığı konusunda agnostiktir. ViewModel tarafından gösterilen bir resim setini bilir ve bunları kullanıcıya gösterir.
Temel farklılıklardan birinin MVC'de V'nizin M'nizi doğrudan okuduğunu ve verileri manipüle etmek için C üzerinden geçtiğini, oysa MVVM'de VM'nizin bir M proxy'si gibi davrandığını ve size mevcut işlevselliği sağladığını düşündüm. V.
Önemsiz değilse, hiç kimsenin VM'nizin sadece bir M proxy'si olduğu ve C'nin tüm işlevleri sağladığı bir melez oluşturmadığına şaşırıyorum.
MVC kontrollü bir ortam ve MVVM reaktif bir ortamdır.
Kontrollü bir ortamda daha az koda ve ortak bir mantık kaynağına sahip olmalısınız; ki bunlar daima kontrolör içinde yaşamalıdır. Ancak; web dünyasında MVC kolayca görünüm oluşturma mantığı ve görünüm dinamik mantık ayrılır. Oluşturma sunucuda ve dinamik yaşam istemcide yaşar. AngularJS ile birleştirilmiş ASP.NET MVC ile bunu çok görüyorsunuz, oysa sunucu bir Görünüm oluşturacak ve bir Modelde geçecek ve istemciye gönderecektir. İstemci daha sonra Görünüm ile etkileşime girecektir; bu durumda AngularJS yerel bir denetleyici olarak devreye girer. Gönderildikten sonra Model veya yeni bir Model sunucu kontrolörüne aktarılır ve işlenir. (Bu nedenle döngü devam eder ve soketler veya AJAX vb.İle çalışırken bu işlemin birçok başka çevirisi vardır, ancak tüm mimari üzerinde aynıdır.)
MVVM reaktif bir ortamdır, yani bazı olaylara göre etkinleştirilecek kodu (tetikleyiciler gibi) yazarsınız. MVVM'nin geliştiği XAML'de, tüm bunlar dahili veri tabanı çerçevesi ile kolayca yapılabilir, ancak belirtildiği gibi, bu herhangi bir programlama diliyle herhangi bir Görünümdeki herhangi bir sistem üzerinde çalışacaktır. MS'e özgü değildir. ViewModel tetiklenir (genellikle özellik değiştirilmiş bir olaydır) ve Görünüm, oluşturduğunuz tetikleyicilere göre buna tepki verir. Bu teknik olabilir ama sonuçta Görünüm vatansız ve mantıksız. Sadece değerleri temel alarak durumu değiştirir. Ayrıca, ViewModels çok az mantıkla vatansızdır ve Modeller yalnızca durumu sürdürmeleri gerektiği için esasen Sıfır mantığı olan Devlettir. Bunu uygulama durumu (Model), durum tercümanı (ViewModel) ve sonra görsel durum / etkileşim (Görünüm) olarak tanımlıyorum.
Bir MVC masaüstü veya istemci tarafı uygulamasında bir Modeliniz olmalı ve Model Kontrolör tarafından kullanılmalıdır. Modele bağlı olarak, denetleyici Görünümü değiştirir. Görünümler genellikle Arayüzlü Denetleyicilere bağlanır, böylece Denetleyici çeşitli Görünümlerle çalışabilir. ASP.NET'te, Denetleyici Modelleri yönetirken ve Modelleri seçilen bir Görünüme geçirirken MVC mantığı sunucuda biraz geriye dönüktür. Görünüm daha sonra modele dayalı verilerle doldurulur ve kendi mantığı vardır (genellikle AngularJS ile yapılan gibi başka bir MVC seti). İnsanlar bunu MVC uygulamasıyla tartışacak ve karıştıracaklar ve her ikisini de yapmaya çalışacaklar. MVC kullanırken DAİMA mantığı ve kontrolü tek bir konuma koyun. Denetleyici veya Model verilerini barındırmak için Görünüm mantığını Görünüm'ün arkasındaki koda (veya Web için JS ile Görüntüle) yazmayın. Denetleyicinin Görünümü değiştirmesine izin verin. Bir Görünümde yaşaması gereken SADECE mantık, kullandığı Arayüz yoluyla oluşturmak ve çalıştırmak için gereken her şeydir. Bunun bir örneği bir kullanıcı adı ve şifre göndermektir. Masaüstü veya web sayfası (istemcide) olsun, Görünüm Gönder eylemini her tetiklediğinde Denetleyici gönderme işlemini gerçekleştirmelidir. Doğru bir şekilde yapılırsa, her zaman kolayca bir MVC web veya yerel uygulama etrafında yolunuzu bulabilirsiniz. Masaüstü veya web sayfası (istemcide) olsun, Görünüm Gönder eylemini her tetiklediğinde Denetleyici gönderme işlemini gerçekleştirmelidir. Doğru bir şekilde yapılırsa, her zaman kolayca bir MVC web veya yerel uygulama etrafında yolunuzu bulabilirsiniz. Masaüstü veya web sayfası (istemcide) olsun, Görünüm Gönder eylemini her tetiklediğinde Denetleyici gönderme işlemini gerçekleştirmelidir. Doğru bir şekilde yapılırsa, her zaman kolayca bir MVC web veya yerel uygulama etrafında yolunuzu bulabilirsiniz.
MVVM tamamen reaktif olduğu için şahsen benim favorim. Bir Model durumu değiştirirse, ViewModel bu durumu dinler ve çevirir ve hepsi bu !!! Görünüm daha sonra durum değişikliği için ViewModel'i dinler ve ayrıca ViewModel'den çeviriye göre güncellenir. Bazı insanlar buna saf MVVM diyorlar, ancak gerçekten sadece bir tane var ve nasıl tartıştığınız umurumda değil ve her zaman Görünümün kesinlikle mantık içermediği Saf MVVM.
İşte size küçük bir örnek: Diyelim ki bir tuşa basıldığında bir menü slaydı istiyorsunuz. MVC'de arayüzünüzde bir MenuPressed eylemi olacaktır. Denetleyici, Menü düğmesini tıklattığınızda ve ardından Görünüm'de Menü'de SlideMenuIn gibi başka bir Arayüz yöntemine göre kaymasını söylediğini bilecektir. Hangi nedenle gidiş-dönüş? Öyleyse Denetleyici başka bir şey yapamayacağınıza veya yapmak istemediğinize karar verir. Kontrol Ünitesi, Kontrol Ünitesi söylemedikçe, Görünüm hiçbir şey yapmadan Görünümden sorumlu olmalıdır. ANCAK; MVVM'de animasyondaki slayt menüsü yerleşik ve genel olmalıdır ve kaydırılması söylenmek yerine bazı değerlere dayanacaktır. Bu yüzden ViewModel'i dinler ve ViewModel derken IsMenuActive = true (veya bununla birlikte) bunun için animasyon gerçekleşir. Şimdi, Bununla birlikte başka bir noktaya değinmek istiyorum GERÇEKTEN TEMİZLE ve LÜTFEN dikkat edin. IsMenuActive muhtemelen BAD MVVM veya ViewModel tasarımıdır. Bir ViewModel tasarlarken hiçbir zaman bir Görünümün hiçbir özelliğe sahip olacağını varsaymamalısınız ve sadece çevrilmiş model durumunu geçmelisiniz. Bu şekilde, Menünüzü kaldırmak için Görünümünüzü değiştirmeye karar verirseniz ve verileri / seçenekleri başka bir yolla gösterirseniz, ViewModel umursamaz. Peki Menüyü nasıl yönetirsiniz? Veriler mantıklı olduğunda böyle. Bunu yapmanın bir yolu, Menüye bir seçenekler listesi (muhtemelen bir dizi iç ViewModel dizisi) vermektir. Bu listede veri varsa Menü tetikleyici aracılığıyla açmayı bilir, değilse tetikleyici aracılığıyla gizlenmeyi bilir. Sadece menü için verileriniz var veya ViewModel'de değil. Bu verileri ViewModel'de göstermeye / gizlemeye karar vermeyin. sadece Modelin durumunu çevirin. Bu şekilde Görünüm tamamen reaktif ve jeneriktir ve birçok farklı durumda kullanılabilir.
Her birinin mimarisine zaten en azından biraz aşina değilseniz ve net bir şekilde ALOT OF BAD bilgileri bulacağınızdan öğrenmek çok kafa karıştırıcı olabilirse, bunların hepsi kesinlikle mantıklı değildir.
Yani ... bunu doğru yapmak için akılda tutulması gereken şeyler. Uygulamanızı nasıl tasarlayacağınıza karar verin ve STICK TO IT.
Harika MVC yaparsanız, Kontrolörünüzün yönetilebilir olduğundan ve Görünümünüzün tam kontrolünde olduğundan emin olun. Büyük bir Görünüme sahipseniz, Görünüme farklı Denetleyicilere sahip denetimler eklemeyi düşünün. SADECE bu denetleyicileri farklı denetleyicilere kademelendirmeyin. Bakımı çok sinir bozucu. Bir dakikanızı ayırın ve işleri ayrı bileşenler olarak çalışacak şekilde ayrı ayrı tasarlayın ... Ve Denetleyicinin her zaman Model'e depolamayı taahhüt etmesini veya saklamasını söyleyin. MVC in için ideal bağımlılık ayarı Görünüm ← Denetleyici → Model veya ASP.NET ile (beni başlatma) Model ← Görünüm ↔ Denetleyici → Model (Model, Denetleyiciden Görünüm'e tamamen aynı veya tamamen farklı bir Model olabilir)... elbette bu noktada Görünümde Kontrolör'ü bilmenin tek ihtiyacı, çoğunlukla bir Modelin nereye geçeceğini bilmek için uç nokta referansıdır.
Eğer MVVM yaparsan, senin tür ruhunu kutsuyorum, ama SAĞ yapmak için zaman ayırın! Biri için arabirimler kullanmayın. Görünümünüzün değerlere dayalı olarak nasıl görüneceğine karar vermesine izin verin. View with Mock verileriyle oynayın. Eğer o zaman istemiyor olsanız bile (örnek olarak) size bir menü gösteren bir görünüm sahip olursanız o zaman İYİ. Görüşünüz olması gerektiği gibi çalışıyor ve değerlere olması gerektiği gibi tepki veriyor. ViewModel belirli bir çevrilmiş durumda olduğunda bunun gerçekleşmediğinden emin olmak için tetikleyicinize birkaç gereksinim daha ekleyin veya ViewModel'e bu durumu boşaltması için komut verin. ViewModel'inizde, sanki oradan Görünüm'ün görüp görmeyeceğine karar veriyorsanız, bunu dahili mantıkla SİLMEYİN. ViewModel'de bir menü olduğunu varsayamayacağınızı unutmayın. Ve sonunda, Model sadece durumu değiştirmenize ve büyük olasılıkla mağaza durumunu değiştirmenize izin vermelidir. Doğrulama ve her şey burada gerçekleşecek; örneğin, Model durumu değiştiremezse, kendisini kirli veya başka bir şey olarak işaretler. ViewModel bunu fark ettiğinde, kirli olanı çevirir ve ardından View bunu fark eder ve başka bir tetikleyici aracılığıyla bazı bilgileri gösterir. Görünümdeki tüm veriler ViewModel'e bağlanabilir, böylece her şey yalnızca dinamik olabilir ve ViewModel, View'un bağlayıcıya nasıl tepki vereceği konusunda hiçbir fikre sahip değildir. Aslında Modelin bir ViewModel fikri de yok. Bağımlılıklar kurarken, bu şekilde ve sadece böyle işaret etmelidirler. t durumu değiştirmek o zaman sadece kirli veya başka bir şey olarak işaretler. ViewModel bunu fark ettiğinde kirli olanı çevirir ve Görünüm bunu fark eder ve başka bir tetikleyici aracılığıyla bazı bilgileri gösterir. Görünümdeki tüm veriler ViewModel'e bağlanabilir, böylece her şey yalnızca dinamik olabilir ve ViewModel, View'un bağlayıcıya nasıl tepki vereceği konusunda hiçbir fikre sahip değildir. Aslında Modelin bir ViewModel fikri de yok. Bağımlılıklar kurarken, bu şekilde ve sadece böyle işaret etmelidirler. t durumu değiştirmek o zaman sadece kirli veya başka bir şey olarak işaretler. ViewModel bunu fark ettiğinde, kirli olanı çevirir ve ardından View bunu fark eder ve başka bir tetikleyici aracılığıyla bazı bilgileri gösterir. Görünümdeki tüm veriler ViewModel'e bağlanabilir, böylece her şey yalnızca dinamik olabilir ve ViewModel, View'un bağlayıcıya nasıl tepki vereceği konusunda hiçbir fikre sahip değildir. Aslında Modelin bir ViewModel fikri de yok. Bağımlılıklar kurarken, bu şekilde ve sadece böyle işaret etmelidirler. Görünümdeki tüm veriler ViewModel'e bağlanabilir, böylece her şey yalnızca dinamik olabilir ve ViewModel, View'un bağlayıcıya nasıl tepki vereceği konusunda hiçbir fikre sahip değildir. Aslında Modelin bir ViewModel fikri de yok. Bağımlılıklar kurarken, bu şekilde ve sadece böyle işaret etmelidirler. Görünümdeki tüm veriler ViewModel'e bağlanabilir, böylece her şey yalnızca dinamik olabilir ve ViewModel, View'un bağlayıcıya nasıl tepki vereceği konusunda hiçbir fikre sahip değildir. Aslında Modelin bir ViewModel fikri de yok. Bağımlılıklar kurarken, bu şekilde ve sadece böyle işaret etmelidirler.Görünüm → ViewModel → Modeli (ve bir yan burada not ... ve bu muhtemelen sıra savundu alacak ama umurumda değil ... DO NOT PASS MODEL GÖRÜNÜM o MODEL değişmez sürece, aksi takdirde a ile sarın Görünüm model bir dönem görmemelidir. Bir sıçanlara gördüğünüz demoyu ya da nasıl yaptığınızı araştırıyorum, bu yanlış.)
İşte son ipucum ... İyi tasarlanmış, ancak çok basit bir MVC uygulamasına bakın ve bir MVVM uygulaması için de aynısını yapın. Biri sınırlı esneklikle daha fazla kontrole sahipken, diğeri hiçbir kontrole ve sınırsız esnekliğe sahip olmayacak.
Kontrollü bir ortam, tüm uygulamayı bir dizi denetleyiciden veya (tek bir kaynaktan) yönetmek için iyidir; reaktif bir ortam, uygulamanın geri kalanının ne yaptığına dair hiçbir fikre sahip olmadan ayrı depolara ayrılabilir. Mikro yönetim ve serbest yönetime karşı.
Sizi yeterince karıştırmadıysam, benimle iletişime geçmeyi deneyin ... Bunu örnek ve örneklerle ayrıntılı olarak ele almayı umursamıyorum.
Günün sonunda hepimiz programcıyız ve kodlama sırasında içimizde anarşi yaşıyor ... Kurallar çiğnenecek, teoriler değişecek ve tüm bunlar domuz yıkamasıyla sonuçlanacak ... Ama büyük üzerinde çalışırken projelerde ve büyük ekiplerde, bir tasarım deseni üzerinde anlaşmaya ve onu uygulamaya yardımcı olur. Bir gün, başlangıçta atılan küçük ekstra adımların daha sonra tasarrufların sıçraması ve sınırları haline gelmesini sağlayacaktır.
Basit Fark: (Yaakov'un Coursera AngularJS kursundan esinlenilmiştir)
MVC (Model Görüntüleme Denetleyicisi)
MVVM (Model Görünümü Görünüm Modeli)
ViewModel :
MVVM, Sunum Modeli modelinin bir ayrıntılandırmasıdır (tartışılabilir) . Tartışmalı diyorum, çünkü tek fark WPF'nin veri bağlama ve komut işleme becerisini sağlamasıdır.
Viewmodel, kullanıcı arayüzü öğeleriniz için "soyut" bir modeldir. Görünümünüzdeki komutları ve eylemleri görsel olmayan bir şekilde yürütmenize izin vermelidir (örneğin, sınamak için).
MVC ile çalıştıysanız, muhtemelen görünümünüzün durumunu yansıtmak için model nesneleri oluşturmak, örneğin bazı düzenleme iletişim kutularını göstermek ve gizlemek vb. İçin yararlı bulmuşsunuzdur.
MVVM paterni, bu uygulamanın tüm UI öğelerine genelleştirilmesidir.
Ve bu bir Microsoft modeli değil, ek olarak WPF / Silverlight veri bağlarının bu modelle çalışmak için özellikle uygun olduğu. Ancak hiçbir şey, örneğin, java sunucu yüzleriyle kullanılmasını engellemez.
Mimari kalıplar konusuna aşina olmayan biri için diğer cevapların anlaşılması kolay olmayabilir. Uygulama mimarisinde yeni olan biri, seçiminin uygulamada uygulamasını nasıl etkileyebileceğini ve topluluklardaki tüm yaygaraların ne olduğunu bilmek isteyebilir.
Yukarıdakilere biraz ışık tutmaya çalışarak MVVM, MVP ve MVC'yi içeren bu senaryoyu hazırladım. Hikaye, bir kullanıcı bir film arama uygulamasında 'BUL' düğmesini tıklatarak başlar:
Kullanıcı: Tıklayın…
Görünüm : Kim bu? [ MVVM | MVP | MVC ]
Kullanıcı: Ara düğmesini tıkladım…
Görünüm : Tamam, bir saniye ... [ MVVM | MVP | MVC ]
( ViewModel | Presenter | Controller … 'ı çağıran görünüm ) [ MVVM | MVP | MVC ]
Görünüm : Hey ViewModel | Sunucu | Denetleyici , bir Kullanıcı ara düğmesini henüz tıkladı, ne yapmalıyım? [ MVVM | MVP | MVC ]
ViewModel | Sunucu | Kontrolör : Hey Görünüm , bu sayfada herhangi bir arama terimi var mı? [ MVVM | MVP | MVC ]
Görünüm : Evet,… işte burada… “piyano” [ MVVM | MVP | MVC ]
—— MVVM ve MVP arasındaki en önemli fark bu | MVC ———
Presenter : Thanks View ,… Bu arada Model üzerindeki arama terimini arıyorum , lütfen ona bir ilerleme çubuğu gösterin [ MVP | MVC ]
( Sunucu | Denetleyici Modeli çağırıyor …) [ MVP | MVC ]
ViewController : Teşekkürler, ben üzerinde arama terimi ararken olacağım Modeli ancak doğrudan size bilgi vermez. Bunun yerine, herhangi bir sonuç varsa olayları searchResultsListObservable'a tetikleyeceğim. Yani bunu gözlemlemen iyi olur. [ MVVM ]
(SearchResultsListObservable'da herhangi bir tetikleyiciyi gözlemlerken, Görünüm , ViewModel bununla konuşmayacağından kullanıcıya bazı ilerleme çubuğu göstermesi gerektiğini düşünür )
------------------------------
ViewModel | Sunucu | Denetleyici : Hey Model , Bu arama terimi için eşleşmeniz mi var ?: “piyano” [ MVVM | MVP | MVC ]
Model : Hey ViewModel | Sunucu | Kontrolör , kontrol edeyim… [ MVVM | MVP | MVC ]
( Model film veritabanına sorgu yapıyor…) [ MVVM | MVP | MVC ]
( Bir süre sonra … )
———— Bu MVVM , MVP ve MVC arasındaki ayrışma noktası ————––
Model : Sizin için bir liste buldum, ViewModel | Sunucu , burada JSON “[{“ ad ”:” Piyano Öğretmeni ”,” yıl ”: 2001}, {“ ad ”:” Piyano ”,” yıl ”: 1993}]” [ MVVM | MVP ]
Model : Elde edilen bazı sonuçlar var, Kontrolör. Örneğimde bir alan değişkeni oluşturdum ve sonuçla doldurdum. Adı “searchResultsList” [ MVC ]
( Sunucu | Kontrolör sayesinde Modeli ve geri alır Görünüm ) [ MVP | MVC ]
Sunucu : Beklediğiniz için teşekkürler View , sizin için eşleşen sonuçların bir listesini buldum ve bunları sunulabilir bir biçimde düzenledim: [“Piano Teacher 2001 ″,” Piano 1993 ”]. Ayrıca lütfen ilerleme çubuğunu şimdi gizleyin [ MVP ]
Kontrolör : Beklediğiniz için teşekkürler View , Model'e arama sorgunuzu sordum. Eşleşen sonuçların bir listesini bulduğunu ve bunları örneğinin içindeki “searchResultsList” adlı bir değişkende sakladığını söylüyor. Oradan alabilirsiniz. Ayrıca lütfen ilerleme çubuğunu şimdi gizleyin [ MVC ]
ViewModel : searchResultsListObservable üzerindeki herhangi bir gözlemci, bu yeni listenin sunulabilir biçimde olduğu konusunda bilgilendirilmelidir: [“Piano Teacher 2001 ″,” Piano 1993 ”]. [ MVVM ]
Görünüm : Çok teşekkür ederim Sunucu [ MVP ]
Görünüm : Teşekkürler “ Denetleyici ” [ MVC ] (Şimdi Görünüm kendisini sorguluyor: Modelden elde ettiğim sonuçları kullanıcıya nasıl sunmalıyım? Filmin yapım yılı önce mi yoksa son mu olmalı…?)
Görünüm : Ah, searchResultsListObservable'da yeni bir tetikleyici var…, iyi, sunulabilir bir liste var, şimdi sadece bir listede göstermem gerekiyor. Ayrıca sonuç aldığım için ilerleme çubuğunu da gizlemeliyim. [ MVVM ]
Eğer ilgileniyorsanız, ben bir film arama android uygulaması uygulayarak MVVM, MVP ve MVC karşılaştırarak burada bir dizi makale yazdım .
Bu modelde , MSFT'nin MVC makinesi bizden gizlediği için istek veya yanıt nesneleriyle artık HTTP düzeyinde temas yoktur .
Yukarıdaki 6. maddenin açıklanmasında (istek üzerine) ...
Bunun gibi bir ViewModel varsayalım:
public class myViewModel{
public string SelectedValue {get;set;}
public void Post(){
//due to MVC model binding the SelectedValue string above will be set by MVC model binding on post back.
//this allows you to do something with it.
DoSomeThingWith(SelectedValue);
SelectedValue = "Thanks for update!";
}
}
Direğin denetleyici yöntemi şu şekilde görünecektir (Aşağıya bakın), mvm örneğinin MVC bağlama mekanizmaları tarafından otomatik olarak başlatıldığını unutmayın. Sonuç olarak hiçbir zaman sorgu dizesi katmanına düşmeniz gerekmez! Bu, MVC, sorgu dizelerini temel alarak sizin için ViewModel'i başlatır!
[HTTPPOST]
public ActionResult MyPostBackMethod (myViewModel mvm){
if (ModelState.IsValid)
{
// Immediately call the only method needed in VM...
mvm.Post()
}
return View(mvm);
}
Yukarıdaki bu eylem yönteminin istediğiniz gibi çalışabilmesi için, gönderide döndürülmeyen şeyleri değerlendiren bir boş CTOR'un olması gerektiğini unutmayın. Geri gönderme ayrıca değişen şeyler için ad / değer çiftlerini de geri göndermelidir. Eksik ad / değer çiftleri varsa, MVC ciltleme motoru basit bir şey olmayan doğru şeyi yapar! Böyle bir durumda kendinizi "Post back'lerde veri kaybediyorum" diyerek bulabilirsiniz ...
Bu modelin avantajı ViewModel'in Model / Buisness mantığına arayüz oluşturan tüm "dağınıklık" çalışmasını gerçekleştirmesidir, kontrolör sadece bir çeşit yönlendiricidir. Bu eylem SOC.
MVVM, görünüm modelini karışıma ekler. Bu, UI'ye özgü tüm parçaları normal modelinize koymadan WPF'nin birçok bağlayıcı yaklaşımını kullanmanıza izin verdiği için önemlidir.
Yanılıyor olabilirim, ancak MVVM'nin denetleyiciyi karışıma gerçekten zorladığından emin değilim. Kavramın daha uyumlu olduğunu düşünüyorum: http://martinfowler.com/eaaDev/PresentationModel.html . İnsanların MVC ile birleştirmeyi seçtiğini düşünüyorum, desende yerleşik değil.
Söyleyebileceğim kadarıyla, MVVM MVC'nin MV'si ile eşleşir - yani geleneksel bir MVC deseninde V doğrudan M ile iletişim kurmaz. MVC'nin ikinci versiyonunda M ve V arasında doğrudan bir bağlantı vardır. MVVM M ve V iletişimi ile ilgili tüm görevleri alıyor ve bunu C'den ayırmak için birleştiriyor gibi görünüyor. Aslında, MVVM'de tam olarak hesaba katılmayan daha geniş kapsam uygulama iş akışı (veya kullanım senaryolarının uygulanması) var. Bu kontrolörün rolüdür. Bu düşük düzey yönleri denetleyicilerden kaldırarak daha temizdir ve uygulamanın kullanım senaryosunu ve iş mantığını değiştirmeyi kolaylaştırır ve denetleyicileri daha yeniden kullanılabilir hale getirir.
MVVM'nin kökeninden bahsetmeden çok oylanan bir cevap olduğu beni şaşırtıyor . MVVM Microsoft toplumda kullanılan popüler bir terim olup, bir kökenli Martin Fowler gelen Sunum Modeli . Bu nedenle, desenin nedenini ve diğerleriyle arasındaki farkı anlamak için, desen hakkındaki orijinal makale okunacak ilk şeydir.
Genellikle MVC, Web geliştirmede kullanılır ve MVVM en çok WPF / Silverlight geliştirmede popülerdir. Bununla birlikte, bazen web mimarisi MVC ve MVVM'nin bir karışımına sahip olabilir.
Örneğin: knockout.js'yi kullanabilirsiniz ve bu durumda istemci tarafında MVVM'ye sahip olursunuz. Ayrıca MVC'nizin sunucu tarafı da değişebilir. Karmaşık uygulamalarda, hiç kimse saf Modeli kullanmaz. ViewModel'i MVC'nin "Modeli" olarak kullanmak mantıklı olabilir ve gerçek Modeliniz temel olarak bu VM'nin bir parçası olacaktır. Bu size ekstra bir soyutlama katmanı verir.
MVVMC veya belki de MVC +, işletme ve hızlı uygulama geliştirme için uygun bir yaklaşım gibi görünmektedir. Kullanıcı arayüzünü iş ve etkileşim mantığından ayırmak güzel olsa da, 'saf' MVVM modeli ve mevcut örneklerin çoğu tekil görünümlerde en iyi sonucu verir.
Tasarımlarınızdan emin değilim, ancak uygulamaların çoğunda sayfalar ve birkaç (yeniden kullanılabilir) görünüm var ve bu nedenle ViewModels'ın bir dereceye kadar etkileşim kurması gerekiyor. Sayfayı denetleyici olarak kullanmak MVVM'nin amacını tamamen yener, bu nedenle altta yatan mantık için bir "VM-C" yaklaşımı kullanılmaması uygulamada olgunlaştıkça .. zor yapılara yol açabilir. VB-6'da bile çoğumuz muhtemelen Button olayına iş mantığını kodlamayı bıraktık ve komutları bir denetleyiciye 'aktarmaya' başladık, değil mi? Son zamanlarda bu konuda ortaya çıkan birçok çerçeveye baktım; benim favorim Magellan (at kodeksplex) yaklaşımı. Mutlu kodlama!
http://en.wikipedia.org/wiki/Model_View_ViewModel#References
ViewModel bir Controller'dan tamamen farklı bir işleve sahip olduğundan, Controller MVVM'de bir ViewModel ile değiştirilmez. Hala bir Denetleyiciye ihtiyacınız var, çünkü bir Denetleyici olmadan Modeliniz, ViewModel ve View pek bir şey yapmaz ... MVVM'de de bir Denetleyiciniz var, MVVM adı sadece yanıltıcı.
MVVMC benim düşünceme göre doğru isim.
Gördüğünüz gibi ViewModel sadece MVC modeline bir ektir. Dönüşüm mantığını (örneğin nesneyi bir dizeye dönüştürür) Denetleyiciden ViewModel'e taşır.
Bunun için Orta bir makale yaptım.
MVVM
View ➡ ViewModel ➡ Modeli
Bir denetleyici kullanıyorsanız , bir Denetleyici her zaman SwiftUI'de gösterildiği gibi gerekli olmamasına rağmen Views ve ViewModels referanslarına sahip olabilir .
class CustomView: UIView {
var viewModel = MyViewModel {
didSet {
self.color = viewModel.color
}
}
convenience init(viewModel: MyViewModel) {
self.viewModel = viewModel
}
}
struct MyViewModel {
var viewColor: UIColor {
didSet {
colorChanged?() // This is where the binding magic happens.
}
}
var colorChanged: ((UIColor) -> Void)?
}
class MyViewController: UIViewController {
let myViewModel = MyViewModel(viewColor: .green)
let customView: CustomView!
override func viewDidLoad() {
super.viewDidLoad()
// This is where the binder is assigned.
myViewModel.colorChanged = { [weak self] color in
print("wow the color changed")
}
customView = CustomView(viewModel: myViewModel)
self.view = customView
}
}
kurulumdaki farklılıklar
Ortak özellikler
MVVM'nin Avantajları
MVC'nin Avantajları
Pratik açıdan bakıldığında, MVC (Model-View-Controller) bir modeldir. Ancak, ASP.net MVC olarak kullanıldığında MVC, Entity Framework (EF) ve "elektrikli el aletleri" ile birleştirildiğinde veritabanlarını, tabloları ve sütunları bir web sayfasına tam olarak getirmek için çok güçlü, kısmen otomatik bir yaklaşımdır Yalnızca CRUD işlemleri veya R (Al veya Oku) işlemleri. En azından MVVM kullandığım zaman, View Modeller, iş nesnelerine bağlı modellerle etkileşime girdi, bu da "el yapımı "ydı ve çok çaba sarf ettikten sonra, EF'in bir tane verdiği kadar iyi modeller elde etmek şanslıydı. -of-the-box". Pratik bir programlama bakış açısından, MVC iyi bir seçim gibi görünüyor çünkü bir sürü kullanıma hazır veriyor, ancak yine de çan ve ıslıkların eklenmesi için bir potansiyel var.
Verilen yanıtların birçoğunu tamamlayıcı olarak, Modern istemci tarafı web'den veya Zengin Web Uygulaması'ndan ek bir bakış açısı eklemek istedim. .
Gerçekten de bu günlerde basit web siteleri ve daha büyük web uygulamaları, Bootstrap gibi birçok popüler kitaplıkla yaygın olarak oluşturulmuştur. Steve Sanderson tarafından geliştirilen Knockout , modeldeki en önemli davranışlardan birini taklit eden MVVM deseni için destek sağlar: Görünüm Modeli aracılığıyla veri bağlama. Küçük bir JavaScript ile, Bootstrap'indata-bind
birçok özelliğini kullanmaya benzer şekilde, basit HTML özelliklerine sahip sayfa öğelerine eklenebilen veriler ve mantık uygulanabilir . Birlikte, bu iki kütüphane tek başına etkileşimli içerik sunar; ve yönlendirme ile birleştirildiğinde, bu yaklaşım Tek Sayfa Uygulamasını oluşturmak için basit ama güçlü bir yaklaşımla sonuçlanabilir .
Benzer şekilde, Angular gibi Modern bir istemci tarafı çerçevesi , MVC modelini kurallara uygun olarak izler, fakat aynı zamanda bir Hizmet ekler. İlginçtir, Model-View-Whatever (MVW) olarak lanse edilir. ( Stack Overflow'daki bu gönderiye bakın .)
Buna ek olarak, Açısal 2 gibi İlerici web çerçevelerinin yükselişiyle, terminolojide bir değişiklik ve belki de Bileşenlerin bir Görünüm veya Şablon içerdiği ve bir Hizmetle etkileşime girebileceği yeni bir mimari desen görüyoruz. Modül; ve bir dizi Modül uygulamayı oluşturur.
MVC ve MVVM'nin aynı olduğunu düşünürdüm. Şimdi Flux'un varlığı nedeniyle farkı söyleyebilirim:
MVC'de, uygulamanızdaki her görünüm için bir modeliniz ve bir denetleyiciniz var, bu yüzden ona görünüm, görünüm modeli, görünüm denetleyicisi diyorum. Kalıp size bir görünümün diğeriyle nasıl iletişim kurabileceğini söylemez. Bu nedenle, farklı çerçevelerde bunun için farklı uygulamalar vardır. Örneğin, denetleyicilerin birbirleriyle konuştuğu uygulamalar, diğer uygulamalarda aralarında aracılık eden başka bir bileşen vardır. Görünüm modellerinin birbirleriyle iletişim kurduğu uygulamalar bile vardır, bu da görünüm modeline yalnızca görünüm denetleyicisi tarafından erişilmesi gerektiğinden MVC deseninin bir kırılmasıdır.
MVVM'de, her bileşen için bir görünüm modeliniz de vardır. Desen, görünümün kontrolün görünüm modelini nasıl etkilemesi gerektiğini belirtmez, bu nedenle genellikle çoğu çerçeve görünüm modelinde denetleyicinin işlevselliğini içerir. Bununla birlikte, MVVM, görünüm modelinizin verilerinin, belirli bir görünüm için farkında olmayan veya özel olmayan tüm model olan modelden gelmesi gerektiğini söyler.
Farkı göstermek için, Flux desenini alalım. Akı deseni, uygulamadaki farklı görünümlerin nasıl iletişim kurması gerektiğini söyler. Her görünüm bir mağazayı dinler ve dağıtıcıyı kullanarak eylemleri başlatır. Görev dağıtıcı, tüm mağazalara yeni yapılan eylem hakkında bilgi verir ve mağazalar kendilerini günceller. Flux'ta bir mağaza, MVVM'deki (genel) modele karşılık gelir. belirli bir görünüm için özel değildir. Genellikle insanlar React ve Flux kullandığında, her React bileşeni aslında MVVM modelini uygular. Bir eylem gerçekleştiğinde, görünüm modeli dağıtıcıyı çağırır ve son olarak modeldeki mağazadaki değişikliklere göre güncellenir. Her bileşenin MVC uyguladığını söyleyemezsiniz çünkü MVC'de yalnızca denetleyici görünüm modelini güncelleyebilir.
mvc sunucu tarafında ve mvvm web geliştirmede istemci tarafındadır (tarayıcı).
Javascript çoğu zaman mvvm tarayıcıda kullanılır. mvc için birçok sunucu tarafı teknolojisi vardır.
Çok kısa - içinde MVC Kontrolcü (kontroller) görünümünün farkındadır, MVVM'de ise ViewModel bunu kimin kullandığını bilmemektedir. ViewModel, gözlemlenebilir özelliklerini ve eylemlerini, onu kullanmak isteyebilecek herkese açıklar. ViewModel içinde kullanıcı arayüzüne referans olmadığından, bu gerçek testi kolaylaştırır.
Model – Görünüm – Denetleyici (genellikle MVC olarak bilinir) ), ilgili program mantığını birbirine bağlı üç öğeye bölen kullanıcı arabirimleri geliştirmek için yaygın olarak kullanılan bir yazılım tasarım modelidir. Bu, bilgilerin iç temsillerini bilginin kullanıcıya sunulduğu ve kullanıcı tarafından kabul edilme biçimlerinden ayırmak için yapılır. MVC mimari modelinin ardından bu ana bileşenleri ayırır ve kodların yeniden kullanılmasına ve paralel geliştirilmesine olanak tanır.
Geleneksel olarak masaüstü grafik kullanıcı arabirimleri (GUI'ler) için kullanılan bu desen, web uygulamaları tasarlamak için popüler hale gelmiştir. JavaScript, Python, Ruby, PHP, Java ve C # gibi popüler programlama dillerinin web uygulama geliştirmede doğrudan MVC çerçeveleri vardır.
model
Desenin merkezi bileşeni. Uygulamanın kullanıcı arabiriminden bağımsız olarak dinamik veri yapısıdır. Uygulamanın verilerini, mantığını ve kurallarını doğrudan yönetir.
Görünüm
Grafik, diyagram veya tablo gibi bilgilerin herhangi bir temsili. Yönetim için çubuk grafik ve muhasebeciler için sekmeli görünüm gibi aynı bilgilerin birden çok görünümü mümkündür.
kontrolör
Girişi kabul eder ve model veya görünüm için komutlara dönüştürür.
Uygulamayı bu bileşenlere bölmenin yanı sıra, model-görünüm-denetleyici tasarımı aralarındaki etkileşimleri tanımlar.
Model, uygulamanın verilerini yönetmekten sorumludur. Denetleyiciden kullanıcı girişi alır.
Görünüm, modelin belirli bir biçimde sunumu anlamına gelir.
Denetleyici kullanıcı girişine yanıt verir ve veri modeli nesneleri üzerinde etkileşimler gerçekleştirir. Kontrolör girişi alır, isteğe bağlı olarak doğrular ve girişi modele geçirir.
Model – View – ViewModel (MVVM) bir yazılım mimari modelidir.
MVVM, grafiksel kullanıcı arayüzünün gelişimini (biçimlendirme dili veya GUI kodu aracılığıyla olsun) iş mantığının veya arka uç mantığının (veri modeli) geliştirilmesinden ayırır. MVVM'nin görünüm modeli bir değer dönüştürücüsüdür, yani görünüm modeli, veri nesnelerini modelden nesnelerin kolayca yönetilecek ve sunulacak şekilde göstermekten (dönüştürmeden) sorumludur. Bu açıdan, görünüm modeli bir görünümden daha modeldir ve görünümün tüm görüntüleme mantığı olmasa bile çoğunu işler. Görünüm modeli, görünüm tarafından desteklenen kullanım senaryoları çevresinde arka uç mantığına erişimi düzenleyen bir aracı desen uygulayabilir.
MVVM, Martin Fowler'in Sunum Modeli tasarım modelinin bir çeşididir. MVVM bir görünümün durumunu ve davranışını aynı şekilde soyutlar, ancak Sunu Modeli belirli bir kullanıcı arayüzü platformuna bağımlı olmayan bir şekilde bir görünümü özetler (bir görünüm modeli oluşturur).
MVVM, özellikle kullanıcı arabirimlerinin olay odaklı programlamasını basitleştirmek için Microsoft mimarları Ken Cooper ve Ted Peters tarafından icat edildi. Desen, Windows Presentation Foundation'a (WPF) (Microsoft'un .NET grafik sistemi) ve Silverlight'a (WPF'nin İnternet uygulaması türevi) dahil edildi. Microsoft'un WPF ve Silverlight mimarlarından John Gossman, MVVM'yi 2005'teki blogunda duyurdu.
Model – View – ViewModel, özellikle .NET platformunu içermeyen uygulamalarda model-view-binder olarak da adlandırılır. ZK (Java ile yazılmış bir web uygulaması çerçevesi) ve KnockoutJS (bir JavaScript kütüphanesi) model-view-binder kullanır.