關(guān)于
本文作為開篇,介紹了出場(chǎng)人物,并形象化的引入了高階函數(shù),
得到了柯里化的概念。
后續(xù)文章,會(huì)介紹高階函數(shù)的實(shí)現(xiàn)方式,詞法作用域和閉包,參數(shù)化類型,類型上的柯里化,
敬請(qǐng)期待。
如有不同的認(rèn)識(shí),或者感興趣的點(diǎn),請(qǐng)直接聯(lián)系我,歡迎指教。
人物介紹
球星庫(kù)里

庫(kù)里,Stephen Curry,1988年3月14日出生于美國(guó)俄亥俄州阿克倫(Akron, Ohio),
美國(guó)職業(yè)籃球運(yùn)動(dòng)員,司職控球后衛(wèi),效力于NBA金州勇士隊(duì)。
斯蒂芬·庫(kù)里2009年通過(guò)選秀進(jìn)入NBA后一直效力于勇士隊(duì),新秀賽季入選最佳新秀第一陣容;
2014-15賽季隨勇士隊(duì)獲得NBA總冠軍;
兩次當(dāng)選常規(guī)賽MVP,兩次入選最佳陣容第一陣容,三次入選全明星賽西部首發(fā)陣容。
Haskell Curry

這次我們說(shuō)的不是NBA的庫(kù)里,而是美國(guó)著名的數(shù)學(xué)家,邏輯學(xué)家Haskell Curry,它在組合子邏輯方面有杰出貢獻(xiàn)。
Curry本科就讀于哈佛大學(xué)醫(yī)學(xué)專業(yè),業(yè)余選修了數(shù)學(xué),1917年轉(zhuǎn)到了數(shù)學(xué)系。
畢業(yè)后,在通用電氣找到了一份電氣工程師工作,繼續(xù)在麻省理工進(jìn)修電氣工程,但意識(shí)到自己更適合做理論研究,而非應(yīng)用科學(xué)。
1922年轉(zhuǎn)專業(yè)到了物理學(xué),但物理學(xué)哈佛會(huì)更好些,于是作為助教回到了哈佛,1924年拿到了物理碩士學(xué)位。
隨后,在哈佛攻讀數(shù)學(xué)博士學(xué)位。
1924年,他最開始的研究方向是微分方程理論,與此同時(shí)他接觸了一些邏輯學(xué)。
閱讀了羅素和懷特海的《數(shù)學(xué)原理》之后,他產(chǎn)生了使用組合子來(lái)分析代換規(guī)則的設(shè)想。
于是,放棄了微分方程的研究,準(zhǔn)備撰寫一篇邏輯方面的博士論文。
1929年,他的第一篇論文《邏輯代換的分析》在《美國(guó)數(shù)學(xué)報(bào)》發(fā)表。
之后,Curry在賓夕法尼亞大學(xué)擔(dān)任教員直至1966年退休,期間曾擔(dān)任國(guó)家研究委員,普林斯頓的高級(jí)學(xué)會(huì)會(huì)員。
發(fā)表的論文包括,《組合子邏輯的全稱量詞》《組合子理論的補(bǔ)遺》《顯式變量的組合邏輯觀點(diǎn)》《組合邏輯中相等性及推導(dǎo)的幾個(gè)性質(zhì)》。
1942年,Curry作為符號(hào)邏輯學(xué)會(huì)會(huì)長(zhǎng),發(fā)表了離職演說(shuō)《數(shù)理邏輯的組合子基礎(chǔ)》。
Curry闡明了組合子邏輯與Chruch的lambda演算之間的密切聯(lián)系,
建立了一套類似于Church和Rosser的完備系統(tǒng)。
第二次世界大戰(zhàn)期間,Curry又開始研究應(yīng)用數(shù)學(xué),1943年發(fā)表了《Heaviside演算》。
1946年,Curry在應(yīng)用物理實(shí)驗(yàn)室工作后,去了阿伯丁實(shí)驗(yàn)場(chǎng),發(fā)布了《使用ENIAC的逆向插值法研究》和《使用ENIAC的四階插值法研究》。
主要著作有,《組合邏輯》和《數(shù)理邏輯基礎(chǔ)》。
(注:這里說(shuō)的這么仔細(xì),是有原因的。組合子邏輯和lambda演算 ,我們多多少少也會(huì)提到。
柯里化
名字的由來(lái)
以下是維基百科關(guān)于Currying的定義:
In mathematics and computer science, currying is the technique of translating the evaluation of a function that takes multiple arguments (or a tuple of arguments) into evaluating a sequence of functions, each with a single argument.
Currying這個(gè)概念,首先是由Gottlob Frege引入的,以邏輯學(xué)家Haskell Curry命名。
雖然,這個(gè)概念是Moses Sch?nfinkel發(fā)明的。
表達(dá)式的值和類型

為了說(shuō)明Currying我們先引入類型的概念。
我們知道編程語(yǔ)言中的表達(dá)式是有值的,我們常說(shuō),表達(dá)式的值為1,值為'a'。
他們?cè)趦?nèi)存中的存儲(chǔ)方式是一樣的,都是二進(jìn)制方式。
但是,感覺上,他們應(yīng)該是不同的東西,于是,我們用不同的類型加以區(qū)分。
我們稱值1的類型是Int,整型,
值'a'的類型是Char,字符型。
于是,我們就在值的概念上建立了一層抽象,不同的值因此有了不同的屬性。
用數(shù)學(xué)語(yǔ)言來(lái)說(shuō),類型作為值集上的一種等價(jià)關(guān)系,誘導(dǎo)出了對(duì)該值集的一種劃分,
相同類型的值構(gòu)成了一個(gè)等價(jià)類。
(注:我們后面將會(huì)看到函數(shù)類型的引入,讓事情變得不是這么簡(jiǎn)單了。
函數(shù)面面觀
函數(shù)用來(lái)將一個(gè)或多個(gè)值變成另一個(gè)值,函數(shù)也是一種值,它同樣具有類型。
例如,加法函數(shù)add是把兩個(gè)整型值變成一個(gè)整型值,假如我們已經(jīng)定義好了add函數(shù),我們可以這樣調(diào)用它。
(注:我們這里使用的編程語(yǔ)言,函數(shù)調(diào)用是不用加括號(hào)的,具有最高優(yōu)先級(jí)。add 1 2類似于add(1,2)。
add 1 2
= 3
現(xiàn)在我們考慮一個(gè)問(wèn)題,如果我們只給add提供一個(gè)參數(shù),結(jié)果是什么呢?
即,add 1是什么?

我們可以形象化的這樣考慮,先考慮add,
add就像一臺(tái)有兩個(gè)插槽的機(jī)器,
如果兩個(gè)插槽分別提供了1和2,那么它會(huì)彈出結(jié)果3。
問(wèn),如果只有一個(gè)插槽提供了1,那它是什么?
很顯然,它還是一臺(tái)機(jī)器,只不過(guò)只有一個(gè)插槽罷了。
因此,add 1還是一個(gè)函數(shù),只不過(guò)它只接受一個(gè)參數(shù)罷了,
它返回參數(shù)值加1的結(jié)果,它的類型我們可以記為,
add 1 :: Int -> Int
我們?cè)倩剡^(guò)頭來(lái)考慮add的類型,我們看到,
add接受1作為參數(shù),返回add 1這個(gè)函數(shù)。
因此,我們對(duì)add就有另外一種看法了,
它是一臺(tái)有一個(gè)插槽的機(jī)器,接受參數(shù)1后,
彈出的結(jié)果是另一臺(tái)有一個(gè)插槽的機(jī)器add 1。
因此add的類型我們可以記為,
add :: Int -> (Int -> Int)
為了書寫方便,我們假定->具有右結(jié)合律,因此,
add :: Int -> Int -> Int
高階函數(shù)
事實(shí)上,Currying指的是這樣的一個(gè)高階函數(shù),
curry :: ((a, b) -> c) -> (a -> b -> c)
它把函數(shù)f變成函數(shù)g,
f :: ((a, b) -> c)
g :: a -> b -> c
g = curry f
f = uncurry g
使得任意的x,y,滿足,
f (x, y) = g x y