004-數(shù)據(jù)結(jié)構(gòu)與算法-棧和遞歸的關(guān)系

棧的應(yīng)用-遞歸

上一節(jié)我們講到了棧這種數(shù)據(jù)結(jié)構(gòu)滴肿,那么在實(shí)際編程中有哪些應(yīng)用呢?這篇文章我們來(lái)研究一下棧的一種應(yīng)用-遞歸

遞歸的基本思想

遞歸的基本思想佃迄,是把規(guī)模較大的一個(gè)問(wèn)題泼差,分解成規(guī)模較小的多個(gè)子問(wèn)題去解決,而每一個(gè)子問(wèn)題又可以繼續(xù)拆分成多個(gè)更小的子問(wèn)題呵俏。
最重要的一點(diǎn)就是假設(shè)子問(wèn)題已經(jīng)解決了堆缘,現(xiàn)在要基于已經(jīng)解決的子問(wèn)題來(lái)解決當(dāng)前問(wèn)題;或者說(shuō)柴信,必須先解決子問(wèn)題套啤,再基于子問(wèn)題來(lái)解決當(dāng)前問(wèn)題。

總的來(lái)說(shuō)随常,使用遞歸來(lái)解決問(wèn)題就是將復(fù)雜的問(wèn)題簡(jiǎn)單化潜沦。但是有些時(shí)候并不能使用遞歸解決問(wèn)題,那么在什么情況下我們才能去使用遞歸呢绪氛?有以下三種情況:

  1. 定義是遞歸的
    比如很多數(shù)學(xué)定義本身就是遞歸定義唆鸡;例如大家非常熟悉的階乘:
Fact(n)
(1) n=0, 1;
(2) n > 1, n*Fact(n-1);

long Fact(Long n){
if(n=0) return -1;
else return n * Fact(n-1);
}

Fib(n)
(1) n=1 n=2, 1;
(2) n > 2, Fib(n-1) + Fib(n-2);

long Fib(Long n){
 if(n == 1 || n == 2) return 1;
 else return Fib(n-1)+Fib(n-2);
}

對(duì)于類似于這種復(fù)雜的問(wèn)題,能夠分解成幾個(gè)簡(jiǎn)單且解法相同或類似的子問(wèn)題來(lái)求解枣察,便成為遞歸求解争占。
例如在求解4乔妈!時(shí)先求解3湿硝!,然后再進(jìn)一步分解進(jìn)行求解囊骤,這種求解方法也叫做“分治法”猿涨。
采用“分治法”進(jìn)行遞歸求解的問(wèn)題需滿足三個(gè)條件:
-能夠?qū)⒁粋€(gè)問(wèn)題轉(zhuǎn)變?yōu)橐粋€(gè)小問(wèn)題握童,而新問(wèn)題和原問(wèn)題的解法相同或類似。不同的僅僅是處理的對(duì)象叛赚,并且處理更小且變化時(shí)有規(guī)律的
-可以通過(guò)上述轉(zhuǎn)換而使得問(wèn)題更加簡(jiǎn)化
-必須要有一個(gè)明確的遞歸出口澡绩,或成為遞歸邊界

  1. 數(shù)據(jù)結(jié)構(gòu)是遞歸的
    其數(shù)據(jù)結(jié)構(gòu)本身具有遞歸的特性。
    例如俺附,對(duì)于鏈表Node的定義由數(shù)據(jù)域和指針域next組成肥卡,而指針域next是一種指向Node類型的指針,即Node的定義中又用到了其自身事镣。所以鏈表也是一種遞歸的數(shù)據(jù)結(jié)構(gòu)步鉴。
void TraverseList(LinkList p){
    //遞歸終止
    if(p == NULL) 
        return; 
    else{
        // 輸出當(dāng)前節(jié)點(diǎn)的數(shù)據(jù)域
        printf("%d",p->data); 
        //p 指向后繼節(jié)點(diǎn)繼續(xù)遞歸
        TraverseList(p->next);
    }
}
  1. 問(wèn)題的解法是遞歸的
    有一類問(wèn)題,雖然問(wèn)題本身并沒(méi)有明顯的遞歸結(jié)構(gòu),但是采用遞歸求解比迭代求解更簡(jiǎn)單唠叛,比如Hanoi塔問(wèn)題只嚣,八皇后問(wèn)題,迷宮問(wèn)題

遞歸過(guò)程與遞歸工作棧

一個(gè)遞歸函數(shù)艺沼,在函數(shù)的執(zhí)行過(guò)程中,需要進(jìn)行多次自我調(diào)用蕴掏。那么思考一下障般,一個(gè)遞歸函數(shù)是如何執(zhí)行的?
在了解遞歸函數(shù)是如何執(zhí)行之前盛杰,先來(lái)了解一下任何的兩個(gè)函數(shù)之間是如何進(jìn)行調(diào)用的挽荡;
在高級(jí)語(yǔ)言的程序中,調(diào)用函數(shù)和被調(diào)用函數(shù)之間的鏈接與信息交換都是通過(guò)棧來(lái)進(jìn)行的即供。
通常定拟,當(dāng)在一個(gè)函數(shù)的運(yùn)行期間調(diào)用另一個(gè)函數(shù)時(shí),在運(yùn)行被調(diào)用函數(shù)之前逗嫡,系統(tǒng)需要完成三件事情:
-將所有的實(shí)參青自,返回地址等信息調(diào)用傳遞給被調(diào)用函數(shù)保存;
-為被調(diào)用函數(shù)的局部變量分配存儲(chǔ)空間
-將控制轉(zhuǎn)移到被調(diào)用函數(shù)入口

而從被調(diào)用函數(shù)返回調(diào)用函數(shù)之前驱证,系統(tǒng)同樣需要完成三件事:
-保存被調(diào)用函數(shù)的計(jì)算結(jié)果延窜;
-釋放被調(diào)用函數(shù)的數(shù)據(jù)區(qū)
-依照被調(diào)用函數(shù)保存的返回地址將控制移動(dòng)到調(diào)用函數(shù)抹锄。

當(dāng)多個(gè)函數(shù)構(gòu)成嵌套調(diào)用時(shí),按照“先調(diào)用后返回”原則获高,上述函數(shù)之間的信息傳遞和控制轉(zhuǎn)移必須通過(guò)“椖钛恚”來(lái)實(shí)現(xiàn)扫沼,即系統(tǒng)將整個(gè)程序運(yùn)行時(shí)所需要的數(shù)據(jù)空間都安排在一個(gè)棧中缎除,每當(dāng)調(diào)用一個(gè)函數(shù)時(shí)器罐,就在它的棧頂分配一個(gè)存儲(chǔ)區(qū)。每當(dāng)這個(gè)函數(shù)退出時(shí)铸董,就釋放它的存儲(chǔ)區(qū)粟害。則當(dāng)前運(yùn)行時(shí)的函數(shù)的數(shù)據(jù)區(qū)比在棧頂

一個(gè)遞歸函數(shù)的運(yùn)行過(guò)程類似多個(gè)函數(shù)嵌套調(diào)用悲幅;只是調(diào)用函數(shù)和被調(diào)用函數(shù)是同一個(gè)函數(shù).因此,和每次調(diào)用相關(guān)的一個(gè)重要概念是遞歸函數(shù)運(yùn)行的“層次”汰具,假設(shè)調(diào)用該遞歸函數(shù)的主函數(shù)為第0層留荔,則從主函數(shù)調(diào)用遞歸函數(shù)進(jìn)入第1層,從第1層遞歸調(diào)用本函數(shù)為進(jìn)入下一層.即第i+1層.反正退出第1層遞歸應(yīng)返回上一層即第i-1層

為了保證遞歸函數(shù)正確執(zhí)行聚蝶,系統(tǒng)需要設(shè)立一個(gè)“遞歸工作椉燃裕“作為整個(gè)遞歸函數(shù)運(yùn)行期間使用的數(shù)據(jù)存儲(chǔ)區(qū).每一層遞歸所需信息構(gòu)成一個(gè)工作記錄,其中包括所有的實(shí)參句各,所有的局部變量以及上一層的返回地址晴叨。每進(jìn)入一層遞歸兼蕊,就產(chǎn)生一個(gè)新的工作記錄壓入棧頂.每退出一個(gè)遞歸孙技,就從棧頂彈出一個(gè)工作記錄牵啦,則當(dāng)前執(zhí)行層的工作記錄必須是遞歸工作棧棧頂?shù)墓ぷ饔涗浌Q為“活動(dòng)記錄”

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市罪针,隨后出現(xiàn)的幾起案子黄伊,更是在濱河造成了極大的恐慌,老刑警劉巖西篓,帶你破解...
    沈念sama閱讀 216,843評(píng)論 6 502
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件虱黄,死亡現(xiàn)場(chǎng)離奇詭異悦即,居然都是意外死亡橱乱,警方通過(guò)查閱死者的電腦和手機(jī)辜梳,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,538評(píng)論 3 392
  • 文/潘曉璐 我一進(jìn)店門(mén)泳叠,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)作瞄,“玉大人危纫,你說(shuō)我怎么就攤上這事宗挥。” “怎么了种蝶?”我有些...
    開(kāi)封第一講書(shū)人閱讀 163,187評(píng)論 0 353
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)螃征。 經(jīng)常有香客問(wèn)我盯滚,道長(zhǎng),這世上最難降的妖魔是什么? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 58,264評(píng)論 1 292
  • 正文 為了忘掉前任泼疑,我火速辦了婚禮荷荤,結(jié)果婚禮上蕴纳,老公的妹妹穿的比我還像新娘。我一直安慰自己个粱,他們只是感情好古毛,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,289評(píng)論 6 390
  • 文/花漫 我一把揭開(kāi)白布。 她就那樣靜靜地躺著都许,像睡著了一般稻薇。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上胶征,一...
    開(kāi)封第一講書(shū)人閱讀 51,231評(píng)論 1 299
  • 那天塞椎,我揣著相機(jī)與錄音,去河邊找鬼睛低。 笑死案狠,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的钱雷。 我是一名探鬼主播骂铁,決...
    沈念sama閱讀 40,116評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼罩抗!你這毒婦竟也來(lái)了拉庵?” 一聲冷哼從身側(cè)響起,我...
    開(kāi)封第一講書(shū)人閱讀 38,945評(píng)論 0 275
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤套蒂,失蹤者是張志新(化名)和其女友劉穎钞支,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體泣懊,經(jīng)...
    沈念sama閱讀 45,367評(píng)論 1 313
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡伸辟,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,581評(píng)論 2 333
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了馍刮。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片信夫。...
    茶點(diǎn)故事閱讀 39,754評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖卡啰,靈堂內(nèi)的尸體忽然破棺而出静稻,到底是詐尸還是另有隱情,我是刑警寧澤匈辱,帶...
    沈念sama閱讀 35,458評(píng)論 5 344
  • 正文 年R本政府宣布振湾,位于F島的核電站,受9級(jí)特大地震影響亡脸,放射性物質(zhì)發(fā)生泄漏押搪。R本人自食惡果不足惜树酪,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,068評(píng)論 3 327
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望大州。 院中可真熱鬧续语,春花似錦、人聲如沸厦画。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 31,692評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)根暑。三九已至力试,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間排嫌,已是汗流浹背畸裳。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 32,842評(píng)論 1 269
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留淳地,地道東北人躯畴。 一個(gè)月前我還...
    沈念sama閱讀 47,797評(píng)論 2 369
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像薇芝,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子丰嘉,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,654評(píng)論 2 354

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

  • 計(jì)算機(jī)科學(xué)的新學(xué)生通常難以理解遞歸程序設(shè)計(jì)的概念饮亏。遞歸思想之所以困難耍贾,原因在于它非常像是循環(huán)推理(circular...
    啟明_b56f閱讀 7,362評(píng)論 0 20
  • 棧與遞歸 棧還有一個(gè)重要應(yīng)用是在程序設(shè)計(jì)語(yǔ)言中實(shí)現(xiàn)遞歸。一個(gè)直接調(diào)用自己或通過(guò)一系列的調(diào)用語(yǔ)句間接的調(diào)用自己的函數(shù)...
    Mr_Bluyee閱讀 3,109評(píng)論 0 1
  • 記得小時(shí)候經(jīng)常講的一個(gè)故事:從前有座山路幸,山上有座廟荐开,廟里有一個(gè)老和尚和一個(gè)小和尚,一天简肴,老和尚給小和尚講了一個(gè)故事...
    IT可樂(lè)閱讀 484評(píng)論 0 3
  • 前言 幾個(gè)月之前就想寫(xiě)這樣一篇文章分享給大家晃听,由于自己有心而力不足,沒(méi)有把真正的學(xué)到的東西沉淀下來(lái)砰识,所以一直在不斷...
    小鹿動(dòng)畫(huà)學(xué)編程閱讀 1,598評(píng)論 2 14
  • 一能扒、遞歸定義 如果函數(shù)中包含了對(duì)其自身的調(diào)用,該函數(shù)就是遞歸的辫狼; 遞歸(Recursion)初斑,在數(shù)學(xué)與計(jì)算機(jī)科學(xué)中...
    惑也閱讀 10,850評(píng)論 0 4