在閱讀DDD鉅著《Patterns, Principles, and Practices of Domain-Driven Design》的過程當中,Scott在第5章提到了使用函數式編程語言配合貧血模型去實踐DDD的一種思路,這激發了個人無限遐想。html
在軟件開發領域,咱們已經擁有了許多的抽象方法論和大量的實現技術。但我我的認爲,這一切歸根結底,都是人類思惟在軟件開發領域的具體表達方式。而人類在認識和分析軟件所要解決的業務領域問題時,思考的內容不外乎由兩個部分組成:『業務流程』與『業務規則』。前者,回答了業務活動中先作什麼後作什麼的問題;後者,則回答了遇到什麼狀況時應該怎麼作的問題。二者結合後,獲得咱們須要的業務結果,或者叫做「實現業務目標」。java
再想一想目前學習和掌握的面向對象的一系列方法,又是如何將上述思惟結果映射到軟件中去的呢?我認爲是這樣的:git
而後,我認爲,對於複雜業務規則的梳理,能夠象數學概括法同樣進行演繹:假設一個函數y=f(x)
,給定x的定義域,肯定y的值域。特別是在排列組合等方面的一些問題,也常常採用遞歸的方式來解決。因此,從這個角度講,函數式編程更貼近人類思惟習慣,因此讓我天然而然地把目光轉向了它。github
在選擇具體的函數式編程語言時,我首先想到的是它最好是同時能支持面向對象編程的。由於即使LISP做爲函數式編程語言的先祖,誕生已長達半個世紀,但單純的函數式編程語言與面向對象編程語言相比,在抽象領域概念、組合系統模塊、實現信息隱蔽等方面存在必定的差距,因此一直沒有成爲軟件開發的主流。正則表達式
信息隱蔽原理:在西安電子科大蔡希堯與陳平老師於1993年合做出版的《面向對象技術》一書中是這樣描述的:把需求和求解的方法分離;把相關信息——數據結構和算法,集中在一個模塊之中,和其餘模塊隔離,它們不能隨便訪問這個模塊內部的信息。算法
其次,因爲個人語言路線是從Pascal → C → C++ → C#,因此我但願能選擇一種風格近似於C、強類型的函數式編程語言。在比較了F#、R、ErLang等幾種常見的函數式編程語言以後,我最終選擇了Scala。編程
注:如下內容,節選翻譯或參考自《Programming in Scala》第1章、第3章,《Programming Scala》第6章,不算完整意義上的我的心得。設計模式
y=f(x)
,給定x一定獲得y,不會所以產生二義結果。所以不管對於代碼測試仍是併發,因爲給定輸入一定獲得預期輸出,而不受其餘因素干擾,因此能有效減小Bug產生。說了那麼多,個人根本目的仍是要將Scala做爲實現DDD的主要武器。那麼試想一下,Scala在咱們實現DDD的過程當中能有哪些幫助呢?我暫且胡侃亂謅以下:數據結構
val
以及case class
表示,在語法層面就直觀地代表是不可修改的。Unit
)對應CQRS裏的Query,保證類的方法沒有反作用;用Procedure(返回類型爲Unit
)對應CQRS裏的Command,明確代表這一類方法會產生修改狀態等反作用。這一樣從語法層面就能對兩者進行明確區分。def sum_count(ints:Seq[Int) = (ints.sum, ints.size)
這樣一個函數後,咱們能夠這樣調用,以獲得一個1至6的整數序列的整數值合計,及該序列的尺寸: val(sum, count) = sum_count(List(1, 2, 3, 4, 5, 6))
。retire = (Age >= 60) || (ServiceLength >= 30)
。以往的方式是本身寫一個語法解析器,把這條文本轉換成相應的Specification對象,而後扔給聚合去使用。如今有了Scala的幫助,就使編寫語法解析器這一環節的工做量大大減小。val circuit = new Circuit with Adders with Multiplexers with Flipflops with MultiCoreProcessors
這樣就建立了一個帶有加法器、乘法器、觸發器和多核處理器的元件。implicit
爲實現數據類型的方法擴展提供了便捷,成爲Trait以外的另外一個功能擴展手段。如下是我目前主要的學習資料,並衷心歡迎各位留言補充。閉包
最近讀的書不少也很雜,DDD、BDD、Scala、Cucumber以及Java基礎等等都有涉及,真巴不得一口吃成個大胖子。因爲時間和精力有限,因此如今知識消化很成問題,遲遲沒有進入學以至用的環節,只能先這樣紙上談兵了,好歹先把本身在學習過程當中的一些思考、看到的好東西先記載下來,以備未來之需。