2010-01-02 107 views
6

在幾個示例項目中,我已經看到ViewModels被用來將數據對象轉換爲字符串,以便在View中使用。ViewModels和渲染

ViewModel通常會有一個構造函數接收一個參數 - 一個數據對象。然後構造函數將填充ViewModel的各種屬性(主要是字符串和整數)。

這可以防止在視圖中發生任何複雜的邏輯。乍一看,這對我來說似乎是一個好主意,因爲它更充分地實現了View與複雜邏輯的分離。

例如,假設我的視圖試圖呈現數據對象的屬性'Size',Size是1到3之間的數字,代表'Small/Medium/Large'。

而不是在我的視圖中有一個if/switch語句,我只是在我的ViewModel中有一個'SizeString'或類似的東西,if/switch語句將在ViewModel構造函數中。

有沒有人不同意這種方法?

使用其他方法比如助手會更好嗎?如果是這樣,爲什麼?

回答

6

ViewModel的目的是將複雜的域模型(的一部分)分解爲可以以其他形式呈現的基元。

這種分解必須發生在某個地方。它可能涉及一些簡單的邏輯,例如我最喜歡的示例:將顏色(綠色,黃色,紅色)轉換爲離散值(確定,警告,錯誤)。這是ViewModel的本質,所以我的默認方法是將此邏輯封裝到ViewModel本身。

考慮一下替代方案:如果沒有在ViewModel中實現,那麼在哪裏?如果你把邏輯放在別的地方,你最終會得到一個ViewModel,它基本上只是一個沒有邏輯的結構。讓ViewModel封裝域對象的轉換/分解符合Single Responsibility Principle

儘管這是我的默認方法,但我始終意識到可能需要在多個ViewModel中重用邏輯。在這種情況下,這可能表明原始ViewModel實際上是一個由多個子視圖組成的複雜ViewModel。在這種情況下,您可以將公共邏輯提取到僅封裝該小部分的子ViewModel中。

+0

很好的解釋。我對此不確定的原因是,我確信我在某處閱讀ViewModel應該是沒有任何邏輯的普通POCO對象。但顯然這是行不通的。應該允許ViewModel包含表示邏輯。 – Jonathan 2010-01-02 10:15:53

+0

POCO不排除邏輯的存在:) – 2010-01-02 10:27:26

+0

想寫關於SRP,但你已經做到了。正如我一直說的那樣 - 很難同時成爲一名拳擊手和芭蕾舞演員。 :) – 2010-01-02 10:36:36

2

它將所有內容都轉換爲字符串,因爲web中的所有內容都是字符串。

基本上,視圖模型應該處於「準備輸出」狀態。如果網絡僅由數字構成 - 我們會將所有內容轉換爲整數/小數。

整點視圖模型 - 以格式化數據表示。在你的大小枚舉爲小/中/大。這並不是說從視圖中分離邏輯使得這一點非常有價值 - 它能夠以一種方式,一個地方適應網絡數據。


回答評論=>

是啊,坐好。我也這樣做。但值得一提的是 - 我並不反對將這一觀點納入觀點。因爲視圖和視圖模型是「依賴鏈」中的最後一個。我非常務實,完全反對開發人員將領域模型用作視圖模型並且視圖模型的要求與領域模型發生衝突(即開發人員僅爲了表示目的而添加新的「領域對象」時)的情況。

+0

其實我已經實現它作爲一個枚舉,但我排除了這一事實,以免過度複雜的例子。當然,如果我只是讓View直接訪問Enum,那麼仍然有一些邏輯將它轉換爲一個字符串,如下所示:「Enum.GetName(...)」。所以我仍然希望將該屬性作爲ViewModel中的字符串公開,並讓ViewModel負責enum字符串轉換。這會和你坐在一起嗎? – Jonathan 2010-01-02 10:12:16

+0

更新了我的答案... – 2010-01-02 10:32:10