什么是函数式编程,函数合并与柯里化又是什么意思?
函數(shù)式編程在耳邊回響了多年,今天就來詳細(xì)了解一下它吧。
函數(shù)式編程的主要特征是:函數(shù)是一等公民。它建議大家寫純函數(shù)、沒有副作用的函數(shù)。
討論完純函數(shù)的內(nèi)容,我們會看一下最重要的應(yīng)用:函數(shù)的柯里化。
純函數(shù)的概念
純函數(shù)是這樣一種函數(shù),即相同的輸入,永遠(yuǎn)會得到相同的輸出,而且沒有任何可觀察的副作用。其中的副作用指的是:跟函數(shù)外部環(huán)境發(fā)生的交互。包括但不限于:
- 更改文件系統(tǒng)
- 往數(shù)據(jù)庫插入記錄
- 發(fā)送一個 http 請求
- 可變數(shù)據(jù)
- 打印/log
- 獲取用戶輸入
- DOM 查詢
- 訪問系統(tǒng)狀態(tài)
例如:slice是純函數(shù)而splice不是。
純函數(shù)的作用
可緩存性
var memoize = function(f) {var cache = {};return function() {var arg_str = JSON.stringify(arguments);cache[arg_str] = cache[arg_str] || f.apply(f, arguments);return cache[arg_str];}; };var squareNumber = memoize(function(x){ return x*x; }); squareNumber(4); //=> 16 squareNumber(4); // 從緩存中讀取輸入值為 4 的結(jié)果 //=> 16值得注意的一點是,可以通過延遲執(zhí)行的方式把不純的函數(shù)轉(zhuǎn)換為純函數(shù):
var pureHttpCall = memoize(function(url, params){return function() { return $.getJSON(url, params); } });可移植性/自文檔化
純函數(shù)對于依賴很誠實,這樣就能知道它的目的??梢哉f是把所有需要的(可變的)參數(shù)都傳遞進(jìn)來。
可測試性
簡單地給函數(shù)一個輸入,就能有輸出了。
合理性
如果一段代碼可以替換成它執(zhí)行所得的結(jié)果,而且是在不改變整個程序行為的前提下替換的,那么我們就說這段代碼是引用透明的。這樣會對理解代碼非常重要,因為“可以使用等式推導(dǎo)”(equational reasoning)的技術(shù)來分析代碼,就是“一對一”替換的情況下手動執(zhí)行代碼。
并行代碼
最后一點,也是決定性的一點:我們可以并行運行任意純函數(shù)。因為純函數(shù)根本不需要訪問共享的內(nèi)存,而且根據(jù)其定義,純函數(shù)也不會因副作用而進(jìn)入競爭態(tài)(race condition)。
并行代碼在服務(wù)端 js 環(huán)境以及使用了 web worker 的瀏覽器那里是非常容易實現(xiàn)的,因為它們使用了線程(thread)。不過出于對非純函數(shù)復(fù)雜度的考慮,當(dāng)前主流觀點還是避免使用這種并行。
合并
合并就是一個值經(jīng)過多個函數(shù)變化最后輸出結(jié)果。很明顯是一個 reduce 的概念。
比如 a(b(c(d))) 看起來很不舒服,很像 JS 里的回調(diào)地域有特別多的大括號。所以我們要是有一個 compose 函數(shù),可以將表達(dá)式寫成 [c, b, a].compose(d) 該多好,而且如果數(shù)組里的函數(shù)都是純函數(shù),甚至還能滿足結(jié)合律。
function compose(array) {return function(args) {return array.reduce(function (total, f) {return f(total);}, args);} }或者
function compose(array) {return function(args) {let result = args;array.forEach(function(f) {result = f(result);});return result;} }柯里化
curry 的概念很簡單:只傳遞給函數(shù)一部分參數(shù)來調(diào)用它,讓它返回一個函數(shù)去處理剩下的參數(shù)。
function curry(fn) {return function finalCurry(...args) {if (args.length >= fn.length) {return fn(...args);} else {return function (...args2) {return finalCurry(...args, ...args2);}}} }總結(jié)
以上是生活随笔為你收集整理的什么是函数式编程,函数合并与柯里化又是什么意思?的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: (附源码)计算机毕业设计ssm关山社区居
- 下一篇: 大数据之Sqoop 二