函數(shù)式編程基本概念理解二:Compose

composition(組合) 是函數(shù)式編程的基石缺前。但是實(shí)現(xiàn)組合并不是一件簡單直接的事情扼脐。除了前一節(jié)我們介紹的概念祈争,還需要基礎(chǔ)的數(shù)學(xué)知識买置。


從數(shù)學(xué)說起


先看個公式:

若  y = f(x)辟狈,z=g(y) 瓶蚂, 則 z= g(f(x))

這個我們都是認(rèn)可的糖埋,因?yàn)閮蓚€ y是指同一個值。那我們變一下:

 若 y' = f(x) 窃这, z=g(y'') 瞳别, 則 z  ?? 

這里 z應(yīng)該怎么寫? 我們犯難了,因?yàn)?y'y'' 不一定是同一個值杭攻,如果再有一個函數(shù)m祟敛, 使得y'' = m(y')z = g(f(m(y')))。這個函數(shù) m即是 y'y''的映射兆解, 寫出來就是 y => m(y)馆铁。 這樣的函數(shù)在編程語言中是很常見的,比如 Array.map, Int.toString 等都是這樣的函數(shù)锅睛。


Compose (組合)


看了上面的問題埠巨,我們這里討論下組合即滿足集合的條件。組合其實(shí)就是拼接衣撬。


image.png

一般來說乖订,要拼接,要滿足以下規(guī)則:

  1. 順序性具练,鏈接的各個部件之間要有順序乍构。
  2. 可拼接性,前一個尾部連接點(diǎn)和后面的鏈接點(diǎn)個數(shù)量扛点,類型要匹配哥遮。

回到我們的編程世間里,上面說的要鏈接的部件其實(shí)就是變量和函數(shù)陵究。(也就解釋了在函數(shù)式編程中函數(shù)為什么是一等公民眠饮,因?yàn)樗兞恳粯涌梢员毁x值和傳遞。)所以順序性就是函數(shù)和變量的順序铜邮。這個可以有業(yè)務(wù)和邏輯可以來保證仪召。那可拼接性就是前一個變量 / 函數(shù)入?yún)⒌膫€數(shù)和類型要近跟著的一致寨蹋,這不是一個簡單的事情。

首先扔茅,對于函數(shù)來說已旧,入?yún)⑹遣淮_定,從 0 ... n 都是有可能的, 且類型可以同一個轉(zhuǎn)換函數(shù) m解召娜,數(shù)量怎么解決运褪?更嚴(yán)重的問題是函數(shù)的返回值永遠(yuǎn)只有一個。如何讓一個函數(shù)返回值玖瘸,滿足一個函數(shù)入?yún)⒔斩铮柯斆鞯哪憧赡軙R上說道,那用一個 object 就可以了雅倒。

對就是這樣解決的璃诀,我們將函數(shù)入?yún)⑷糠庋b的一個 object 中,然后在前一個函數(shù)中返回同樣類型的 object.


Pipe / Flow


再看我們數(shù)學(xué)公式 z = g(f(m(y)))屯断,這是個簡單邏輯文虏,如果復(fù)雜點(diǎn): z = i(h(g(f(m(y'))))) 等復(fù)雜的嵌套邏輯我們稱之為洋蔥代碼。那能有更簡單靈活的寫法嗎殖演?

pipeflowfp-ts提供的最常用的簡單化的組合函數(shù)。 pipe 是計(jì)算組合中等到的值年鸳,而 flow是組合的邏輯趴久,不包括值.
用公式表示:

若 z = g(f(m(y))) = g*f*m(y)

則 pipe = g*f*m(y), flow = g*f*m

用代碼例子:

import { flow, pipe } from 'fp-ts/function';

interface Point {
    x: number,
    y: number
}

const moveRight5 = (p: Point) => ({ x: p.x - 5, y: p.y });
const moveDown5 = (p: Point) => ({ x: p.x, y: p.y - 5 });

const start = { x: 3, y: 5 };
pipe(start, moveRight5, moveDown5);
pipe(start, flow(moveRight5, moveDown5));

搞定,但并未沒有結(jié)束搔确,因?yàn)榻M合還有一個條件就是可預(yù)測性或者可規(guī)劃性彼棍。

  1. 可規(guī)劃性,能夠按照既定的規(guī)則

當(dāng)我們在玩高級的托馬斯火車的軌道時膳算,我們時預(yù)制了機(jī)關(guān)的座硕,對于不同的火車經(jīng)過的時候按照火車自己的屬性進(jìn)入不行的路徑,而不改變軌道的配置涕蜂。對應(yīng)到上面的例子华匾,我們只能在 Happy path 下運(yùn)行完成。一旦 start 是個 {} 或者 moveRight5 中出現(xiàn)了異常机隙,這個流程就進(jìn)行不下去了蜘拉。

這個問題我們在下一節(jié)繼續(xù)討論。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末有鹿,一起剝皮案震驚了整個濱河市旭旭,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌葱跋,老刑警劉巖持寄,帶你破解...
    沈念sama閱讀 219,539評論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件源梭,死亡現(xiàn)場離奇詭異,居然都是意外死亡稍味,警方通過查閱死者的電腦和手機(jī)咸产,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,594評論 3 396
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來仲闽,“玉大人脑溢,你說我怎么就攤上這事。” “怎么了悼瓮?”我有些...
    開封第一講書人閱讀 165,871評論 0 356
  • 文/不壞的土叔 我叫張陵蛙粘,是天一觀的道長。 經(jīng)常有香客問我社牲,道長,這世上最難降的妖魔是什么悴了? 我笑而不...
    開封第一講書人閱讀 58,963評論 1 295
  • 正文 為了忘掉前任搏恤,我火速辦了婚禮,結(jié)果婚禮上湃交,老公的妹妹穿的比我還像新娘熟空。我一直安慰自己,他們只是感情好搞莺,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,984評論 6 393
  • 文/花漫 我一把揭開白布息罗。 她就那樣靜靜地躺著,像睡著了一般才沧。 火紅的嫁衣襯著肌膚如雪迈喉。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,763評論 1 307
  • 那天温圆,我揣著相機(jī)與錄音挨摸,去河邊找鬼。 笑死岁歉,一個胖子當(dāng)著我的面吹牛得运,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播刨裆,決...
    沈念sama閱讀 40,468評論 3 420
  • 文/蒼蘭香墨 我猛地睜開眼澈圈,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了帆啃?” 一聲冷哼從身側(cè)響起瞬女,我...
    開封第一講書人閱讀 39,357評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎努潘,沒想到半個月后诽偷,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體坤学,經(jīng)...
    沈念sama閱讀 45,850評論 1 317
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 38,002評論 3 338
  • 正文 我和宋清朗相戀三年报慕,在試婚紗的時候發(fā)現(xiàn)自己被綠了深浮。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 40,144評論 1 351
  • 序言:一個原本活蹦亂跳的男人離奇死亡眠冈,死狀恐怖飞苇,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情蜗顽,我是刑警寧澤布卡,帶...
    沈念sama閱讀 35,823評論 5 346
  • 正文 年R本政府宣布,位于F島的核電站雇盖,受9級特大地震影響忿等,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜崔挖,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,483評論 3 331
  • 文/蒙蒙 一贸街、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧狸相,春花似錦薛匪、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,026評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至将谊,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間渐白,已是汗流浹背尊浓。 一陣腳步聲響...
    開封第一講書人閱讀 33,150評論 1 272
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留纯衍,地道東北人栋齿。 一個月前我還...
    沈念sama閱讀 48,415評論 3 373
  • 正文 我出身青樓,卻偏偏與公主長得像襟诸,于是被迫代替她去往敵國和親瓦堵。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,092評論 2 355

推薦閱讀更多精彩內(nèi)容