文章目錄
- 程式的定義
-
- `程式 = 資料結構 + 控制 + 業務邏輯`
- 寫出好程式的關鍵
- 控制control 和 業務logic 的解耦技術
-
- 例:檢查使用者表單資訊
- 程式設計範式的種類
-
- 兩大分支
- 分類:聲明式、命名式、邏輯的、函數式、面向對象的、面向過程的。
程式的定義
很多人認同的兩個觀點:
-
程式 = 資料結構 + 算法
這個表達式認為,如果資料結構設計得好,算法也會變得簡單,而且一個好的通用的算法應該可以用在不同的資料結構上。
-
算法 = 控制 + 業務邏輯
這個表達式則想表達的是資料結構不複雜,複雜的是算法,算法由兩個邏輯組成,一個是真正的業務邏輯,另外一種是控制邏輯。也就是我們的業務邏輯是複雜的。
Robert Kowalski: 任何算法都會有兩個部分, 一個是 Logic 部分,這是用來解決實際問題的。另一個是 Control 部分,這是用來決定用什麼政策來解決問題。Logic 部分是真正意義上的解決問題的算法,而 Control 部分隻是影響解決這個問題的效率。程式運作的效率問題和程式的邏輯其實是沒有關系的。我們認為,如果将 Logic 和 Control 部分有效地分開,那麼代碼就會變得更容易改進和維護。
通過這兩個表達式,我們可以得出:
程式 = 資料結構 + 控制 + 業務邏輯
程式 = 資料結構 + 控制 + 業務邏輯
程式設計範式,或是程式設計的方法。其實都是在圍繞着這三件事來做的。所有的語言或程式設計範式都在解決這些問題, 也就是程式設計範式的本質:
-
是可以标準化的。比如:周遊資料、查找資料、多線程、并發、異步等,都是可以标準化的。控制
- 因為
需要處理資料,是以标準化 控制 ,需要标準化控制
,我們可以通過泛型程式設計來解決這個事。資料結構
- 而
還要處理使用者的控制
。是以可以通過标準化接口 / 協定來實作,我們的 控制 模式可以适配于任何的 業務邏輯 。業務邏輯
寫出好程式的關鍵
有效地分離、
業務邏輯
和
控制
是寫出好程式的關鍵所在!
資料結構
其中,邏輯 Logic 和 控制 Control 是關鍵, 程式的本質複雜性 是邏輯,非本質複雜性 是控制。
這個和系統架構也有相通的地方,邏輯是你的業務邏輯過程的抽象,加上一個由術語表示的資料結構的定義,控制邏輯跟你的業務邏輯是沒關系的,你控制,它執行。
業務邏輯 部分才是真正有意義的
控制 部分隻是影響 業務邏輯 部分的效率
那些混亂不堪的代碼,會把控制和業務邏輯放在一塊。裡面有些變量和流程是跟業務相關的,有些是不相關的。
業務邏輯決定了程式的複雜度,業務邏輯本身就複雜,你的代碼就不可能寫得簡單。于是 控制 + 業務邏輯 的互相交織成為了最終的程式複雜度。
控制control 和 業務logic 的解耦技術
- 通用的解耦方案:
元語言 logic + 解釋器 control
- 元語言: 描述業務邏輯
- 解釋器: 元語言到目智語言的映射
- 具體技術
- State Machine
- 狀态定義
- 狀态變遷條件
- 狀态的 action
- DSL – Domain Specific Language
- HTML,SQL,Unix Shell Script,AWK,正規表達式……
- 程式設計範式
- 面向對象:委托、政策、橋接、修飾、IoC/DIP、MVC……
- 函數式程式設計:修飾、管道、拼裝
- 邏輯推導式程式設計:Prolog語言
- State Machine
例:檢查使用者表單資訊
-
需求:校驗 使用者資訊
name:字段至少3個字元
password:字段至少8個字元,
repeat_password:和password要一緻,
email:要符合郵箱格式;
- 寫法1:業務邏輯 與 控制 混合
function check_form_x() {
//擷取name字段,校驗
var name = $('#name').val();
if (null == name || name.length <= 3) {
return { status : 1, message: 'Invalid name' };
}
//擷取password字段,校驗
var password = $('#password').val();
if (null == password || password.length <= 8) {
return { status : 2, message: 'Invalid password' };
}
//擷取repeat_password字段,校驗
var repeat_password = $('#repeat_password').val();
if (repeat_password != password.length) {
return { status : 3, message: 'Password and repeat password mismatch' };
}
//擷取email字段,校驗
var email = $('#email').val();
if (check_email_format(email)) {
return { status : 4, message: 'Invalid email' };
}
//校驗通過
return { status : 0, message: 'OK' };
}
-
寫法2:業務邏輯 與 控制 分離
做一個 DSL+ 一個 DSL 的解析器
- 業務邏輯 描述成DSL
- 控制邏輯 check_form 作為 DSL 的解析器
整個邏輯頓時清晰了,細節的處理隻需要在check_form中編寫一次
var meta_create_user = {
form_id : 'create_user',
fields : [
{ id : 'name', type : 'text', min_length : 3 },
{ id : 'password', type : 'password', min_length : 8 },
{ id : 'repeat-password', type : 'password', min_length : 8 },
{ id : 'email', type : 'email' }
]
};
var r = check_form(meta_create_user);
程式設計範式的種類
程式設計範式基本上來說,就是兩大分支
兩大分支
一邊是在解決 資料和算法,
一邊是在解決 邏輯和控制。
分類:聲明式、命名式、邏輯的、函數式、面向對象的、面向過程的。
函數式和邏輯式 偏向于你定義要什麼,而不是怎麼做
程式設計範式和面向對象程式設計範式,偏向于怎麼做,而不是要做什麼