小編給大家分享一下python中函數(shù)式編程是什么,希望大家閱讀完這篇文章后大所收獲,下面讓我們一起去探討吧!
成都創(chuàng)新互聯(lián)基于成都重慶香港及美國等地區(qū)分布式IDC機房數(shù)據(jù)中心構(gòu)建的電信大帶寬,聯(lián)通大帶寬,移動大帶寬,多線BGP大帶寬租用,是為眾多客戶提供專業(yè)西部信息服務(wù)器租用報價,主機托管價格性價比高,為金融證券行業(yè)服務(wù)器托管,ai人工智能服務(wù)器托管提供bgp線路100M獨享,G口帶寬及機柜租用的專業(yè)成都idc公司。
函數(shù)式編程理解:
編寫代碼的時候,函數(shù)式編程更多的是從聲明式的方法,而傳統(tǒng)的編程更多的是命令式的方法。例如,上面的篩選學(xué)生年紀(jì),傳統(tǒng)的編程思想是,我創(chuàng)建了什么,我循環(huán)了什么,我判斷了什么,得出了什么結(jié)果;函數(shù)式編程的思想是,我聲明了一個篩選的函數(shù),我聲明了一個判斷的函數(shù),我把這兩個函數(shù)結(jié)合起來,得出了一個結(jié)果。
關(guān)于純函數(shù)
在函數(shù)式編程的概念中,有一個重要的概念是純函數(shù),那么什么是純函數(shù)呢?
我們用代碼來解釋什么是純函數(shù):
const z = 10; add(x, y) { return x + y; } 復(fù)制代碼 上面的add函數(shù)就是一個純函數(shù),它讀取x和y兩個參數(shù)的值,返回它們的和,并且不會受到全局的z變量的影響 把這個函數(shù)改一下 const z = 10; add(x, y) { return x + y + z; } 復(fù)制代碼
這個函數(shù)就變成了不純的函數(shù)了,因為它返回的值會受到全局的z的影響,換句話說,這個函數(shù)會被外部環(huán)境影響,我們就得出了第一個判斷是否純函數(shù)的重要依據(jù)——純函數(shù)不會受到外部環(huán)境的影響。
再用splice和slice來解釋一下:
var xs = [1,2,3,4,5]; // 純的 xs.slice(0,3); //=> [1,2,3] xs.slice(0,3); //=> [1,2,3] xs.slice(0,3); //=> [1,2,3] // 不純的 xs.splice(0,3); //=> [1,2,3] xs.splice(0,3); //=> [4,5] xs.splice(0,3); //=> [] 復(fù)制代碼
slice收到同樣的參數(shù),每次返回相同的值,所以是純函數(shù),splice收到同樣的參數(shù),每次返回不同的值,所以不是純函數(shù),我們就得出了第二個判斷是否純函數(shù)的重要依據(jù)——純函數(shù)相同的輸入,永遠會得到相同的輸出。
總結(jié):
'純函數(shù)是這樣一種函數(shù),即相同的輸入,永遠會得到相同的輸出,而且沒有任何可觀察的副作用' 復(fù)制代碼
關(guān)于柯里化
柯里化的概念很簡單:只傳遞給函數(shù)一部分參數(shù)來調(diào)用它,讓它返回一個函數(shù)去處理剩下的參數(shù)。
const add = x => y => x + y; add(1)(2); // => 3 復(fù)制代碼
上面的例子,就是一個很典型的柯里化函數(shù),在我們第一調(diào)用的時候,接收了第一次傳入的參數(shù)(用閉包記?。祷亓艘粋€新的函數(shù);在第二次調(diào)用的時候,接收第二次傳入的參數(shù),并且和第一次傳入的函數(shù)相加,返回它們的和。
運用上面的思想編寫一個的柯里化函數(shù):
currying(fn, ...args1) { // '判斷傳入的參數(shù)是否滿足傳入函數(shù)需要的參數(shù),比如說add函數(shù)需要兩個參數(shù)相加,那么判斷是否傳入了兩個參數(shù),滿足調(diào)用傳入函數(shù)計算結(jié)果' if (args1.length >= fn.length) { console.log(args1, '--1--'); return fn(...args1); } // '不滿足返回一個新的函數(shù),繼續(xù)調(diào)用柯里化函數(shù),傳入保存的第一次傳入的函數(shù),傳入保存的第一次傳入的參數(shù),傳入第二次傳入的參數(shù),繼續(xù)上面的判斷邏輯,返回計算結(jié)果' return (...args2) => { console.log(args2, '--2--'); return currying(fn, ...args1, ...args2); }; }, // 定義一個一般函數(shù) const add = (x, y) => x + y; // 使用 const increment = currying(add, 1); console.log(increment(2)); const addTen = currying(add, 10); console.log(addTen(2)); // => [2] --2-- // => [1,2] --1-- // => 3 // => [2] --2-- // => [10,2] --1-- // => 12 復(fù)制代碼
柯里化函數(shù)比較重要的思想是:
多次判斷傳入的參數(shù)是否滿足計算需求,滿足,返回計算結(jié)果,如果不滿足,繼續(xù)返回一個新的柯里化函數(shù)
關(guān)于代碼組合
首先,先寫一個簡單的組合函數(shù):
const compose = (f, g) => x => f(g(x));
這個組合函數(shù)接收兩個函數(shù)當(dāng)作參數(shù),然后返回一個新的函數(shù),x是兩個函數(shù)之間都要使用的值,比如說:
const compose = (...fns) => (...args) => fns.reduceRight((res, fn) => [fn.call(null, ...res)], args)[0]; // 使用,實現(xiàn)一個功能,字符串變成大寫,加上個感嘆號,還要截取一部分,再在前面加上注釋 const toUpperCase = x => x.toUpperCase(); const exclaim = x => `${x}!`; const head = x => `slice is: ${x}`; const reverse = x => x.slice(0, 7); const shout = compose(exclaim, toUpperCase, head, reverse) shout('my name is maya') // => SLICE IS: MY NAME! 復(fù)制代碼
組合的原理其實就是數(shù)學(xué)中的結(jié)合律:
(a + b) + c = a + (b + c)
對組合的理解是:
組合是什么,組合就是運用了數(shù)學(xué)里的結(jié)合律,像是搭積木一樣,把不同的函數(shù)聯(lián)系起來,讓數(shù)據(jù)在里面流動
在各種庫里面都有組合的函數(shù),lodash,underscore,ramda等等,比如在underscore里面,組合是這樣的:
// Returns a function that is the composition of a list of functions, each // consuming the return value of the function that follows. _.compose = function() { var args = arguments; var start = args.length - 1; return function() { var i = start; var result = args[start].apply(this, arguments); while (i--) result = args[i].call(this, result); return result; }; }; 復(fù)制代碼
相信大家到這里已經(jīng)初步了解了函數(shù)式編程的概念了,那么我們怎么使用函數(shù)式編程的方式寫代碼呢,舉個例子:
// 偽代碼,思路 // 比如說,我們請求后臺拿到了一個數(shù)據(jù),然后我們需要篩選幾次這個數(shù)據(jù), 取出里面的一部分,并且排序 // 數(shù)據(jù) const res = { status: 200, data: [ { id: xxx, name: xxx, time: xxx, content: xxx, created: xxx }, ... ] } // 封裝的請求函數(shù) const http = xxx; // '傳統(tǒng)寫法是這樣的' http.post .then(res => 拿到數(shù)據(jù)) .then(res => 做出篩選) .then(res => 做出篩選) .then(res => 取出一部分) .then(res => 排序) // '函數(shù)式編程是這樣的' // 聲明一個篩選函數(shù) const a = curry() // 聲明一個取出函數(shù) const b = curry() // 聲明一個排序函數(shù) const c = curry() // 組合起來 const shout = compose(c, b, a) // 使用 shout(http.post) 復(fù)制代碼
如果想要在項目里面正式使用函數(shù)式編程有這樣幾個步驟:
1、先嘗試使用ES6自帶的高階函數(shù)
2、熟悉了ES6自帶的高階函數(shù)后,可以自己嘗試寫幾個高階函數(shù)
3、在這個過程中,盡量使用純函數(shù)編寫代碼
4、對函數(shù)式編程有所了解之后,嘗試使用類似ramda的庫來編寫代碼
5、在使用ramda的過程中,可以嘗試研究它的源代碼
6、嘗試編寫自己的庫,柯里化函數(shù),組合函數(shù)等
看完了這篇文章,相信你對python中函數(shù)式編程是什么有了一定的了解,想了解更多相關(guān)知識,歡迎關(guān)注創(chuàng)新互聯(lián)行業(yè)資訊頻道,感謝各位的閱讀!
網(wǎng)頁標(biāo)題:python中函數(shù)式編程是什么
標(biāo)題網(wǎng)址:http://jinyejixie.com/article10/ieppgo.html
成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供App設(shè)計、定制開發(fā)、外貿(mào)建站、手機網(wǎng)站建設(shè)、域名注冊、網(wǎng)站收錄
聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請盡快告知,我們將會在第一時間刪除。文章觀點不代表本網(wǎng)站立場,如需處理請聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時需注明來源: 創(chuàng)新互聯(lián)