why純函數(Pure Functions)
當我們的程序變得龐大的時候, 將不可避免地引發一些bugs。我們不能保證杜絕bug產生, 但是我們可以通過某些編程方式來減少一些錯誤的發生。
純函數就是其中一種,它也是函數式編程中一部分。那它為什么可以起到減少bug的作用呢, 原因就在於能被稱之為純函數而制定的一些原則,我們來簡單看下
3個原則:
- 變量都只在函數作用域內獲取, 作為的函數的參數傳入
- 不會產生副作用(side effects), 不會改變被傳入的數據或者其他數據
- 相同的輸入保證相同的輸出(same input -> same ouput)
比如以下這個pureAdd
函數就是純函數, x和y都是函數參數,處在函數作用域內
function pureAdd(x, y) {
return x + y;
}
但是一下就是這個impureAdd
就是不是
let x = 1;
function impureAdd(y) {
return x + y;
}
因為函數內需要的x需要從函數外部的去獲取, 這樣的也就導致了函數的相同的輸入不能保證有相同的輸出, 如下
let x = 1;
console.log(impureAdd(3)) // 4
let x = 2;
console.log(impureAdd(3)) // 5
還有純函數不得改變傳入的值, 比較容易出錯的就是引用類型
作為參數傳入
function mutateObject(obj) {
obj['newkey'] = 'newValue';
}
var o = {};
mutateObject(o);
console.log(o) //{newkey: "newValue"}
還有使用一些mutator methods
如數組的push
,shift
,splice
等等
function firstThree(arr) {
return arr.splice(0,3);
}
純函數的一些優點
- 容易可測試(
testable
) - 因為相同的輸入必定是相同的輸出,因此結果可以緩存(
cacheable
) - 自我記錄(
Self documenting
),因為需要的變量都是參數,參數命名良好的情況下即便很久以后再去看這個函數依舊可以很容易知道這個函數需要哪些參數 - 因為不用擔心有副作用(
side-effects
),因此可以更好地工作