最長回文字符串——馬拉車算法

最長回文字符串

????????????給定一個字符串?s蜜暑,找到?s?中最長的回文子串铐姚。

示例 1:

? ??輸入:"babad"

? ??輸出:"bab"

? ??注意:"aba" 也是一個有效答案。

示例 2:

? ??輸入:"cbbd"

? ??輸出:"bb"

? ? ? 解法有很多肛捍,①暴力破解法:可以枚舉所有可能的字符串子串隐绵,然后判斷是否為回文字符串。但這種解法的時間復(fù)雜度很高拙毫,首先是枚舉所有可能的子串依许,時間復(fù)雜度O(n2),再判斷是否為回文字符串缀蹄,時間復(fù)雜度為O(n2)峭跳,總體的時間復(fù)雜度為O(n3)。②反轉(zhuǎn)法:將字符串反轉(zhuǎn)缺前,找出最長公共子串蛀醉,注意這兩段最長公共子串的位置應(yīng)該是關(guān)于中心對稱的,時間復(fù)雜度為O(n2)衅码。③動態(tài)規(guī)劃:動態(tài)規(guī)劃最重要的就是要找到狀態(tài)轉(zhuǎn)移方程拯刁,而回文的最大特點就是如果一個子串是回文,它兩側(cè)的字符如果相同逝段,那么加上這兩個字符組成的新字符串同樣也是回文垛玻,這種方法的時間復(fù)雜度同樣也是O(n2)割捅。④中心擴散法:遍歷字符串中所有的字符,以這些字符為中心夭谤,用兩個指針向外擴散棺牧,用一個數(shù)組來記錄擴散的半徑;這種方法使用起來有一個小缺陷朗儒,比如aba颊乘,abba兩種回文,前者這種方法很好用醉锄,但是后者就需要特別去判斷乏悄。為了解決這個問題,我們可以向每個字符之間插入一個相同的符號恳不,比如#a#b#b#a#檩小,這樣就很好解決了上述問題,這種方法的時間復(fù)雜度也為O(n2)烟勋。這些方法的時間復(fù)雜度都在O(n2)以上规求,但有一種算法它的時間復(fù)雜度為O(n),就是馬拉車算法卵惦。


馬拉車算法:

維基百科中對于 Manacher 算法是這樣描述的:

[Manacher(1975)] 發(fā)現(xiàn)了一種線性時間算法阻肿,可以在列出給定字符串中從字符串頭部開始的所有回文。并且沮尿,Apostolico, Breslauer & Galil (1995) 發(fā)現(xiàn)丛塌,同樣的算法也可以在任意位置查找全部最大回文子串,并且時間復(fù)雜度是線性的畜疾。因此赴邻,他們提供了一種時間復(fù)雜度為線性的最長回文子串解法。替代性的線性時間解決 Jeuring (1994), Gusfield (1997)提供的啡捶,基于后綴樹(suffix trees)姥敛。也存在已知的高效并行算法。

Manacher 算法本質(zhì)上還是中心擴散法届慈,只不過它使用了類似 KMP 算法的技巧徒溪,充分挖掘了已經(jīng)進行回文判定的子串的特點,在遍歷的過程中金顿,記錄了已經(jīng)遍歷過的子串的信息,也是典型的以空間換時間思想的體現(xiàn)鲤桥。算法技巧:

①定義max_right來記錄當(dāng)前遍歷字符串中能到達最右邊的邊界為多少揍拆,定義id記錄達到最右邊界的字符串中心

②算法步驟和中心擴散法一致,但是在計算類似#a#b#c#d#e#d#c#b#a#時茶凳,因為回文字符串左右對稱嫂拴,所以當(dāng)你計算了左邊的P數(shù)組的值時播揪,右邊的計算是可以借鑒左邊的值,如下




通過增加參數(shù)筒狠,降低尋找次數(shù)猪狈,是典型的以空間換取時間的做法。

def Manacher(s):#回文字符串線性時間復(fù)雜度

? ? lenth =len(s)

????if lenth <2:#特判

? ? ? ? return s

????t ="#"

? ? for iin range(lenth):#初始化

? ? ? ? t = t + s[i]

????????t = t +"#"

????t_lenth =2 * lenth +1

? ? p = [0 for i in range(t_lenth)]#記錄擴散半徑

? ? max_right =0

? ? id =0

? ? max_lenth =0

? ? start =1

? ? for iin range(t_lenth):

????????if i < max_right:

????????????mirror =2 * id - i

????????????p[i] =min(p[mirror],max_right-i)

????????left = i - (1 + p[i])

????????right = i + (1 + p[i])

????????while left >=0 and right < t_lenthand t[left] == t[right]:

????????????p[i] = p[i] +1

? ? ? ? ? ? left = left -1

? ? ? ? ? ? right = right +1

? ? ? ? if i + p[i] > max_right:

????????????max_right = i + p[i]

????????????id = i

? ? ? ? if p[i] > max_lenth:

????????????max_lenth = p[i]

????????????start = (i - max_lenth) //2

? ? return s[start:start+max_lenth]

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末辩恼,一起剝皮案震驚了整個濱河市雇庙,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌灶伊,老刑警劉巖疆前,帶你破解...
    沈念sama閱讀 218,204評論 6 506
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異聘萨,居然都是意外死亡竹椒,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,091評論 3 395
  • 文/潘曉璐 我一進店門米辐,熙熙樓的掌柜王于貴愁眉苦臉地迎上來胸完,“玉大人,你說我怎么就攤上這事翘贮∩蘅” “怎么了?”我有些...
    開封第一講書人閱讀 164,548評論 0 354
  • 文/不壞的土叔 我叫張陵择膝,是天一觀的道長誓琼。 經(jīng)常有香客問我,道長肴捉,這世上最難降的妖魔是什么腹侣? 我笑而不...
    開封第一講書人閱讀 58,657評論 1 293
  • 正文 為了忘掉前任,我火速辦了婚禮齿穗,結(jié)果婚禮上傲隶,老公的妹妹穿的比我還像新娘。我一直安慰自己窃页,他們只是感情好跺株,可當(dāng)我...
    茶點故事閱讀 67,689評論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著脖卖,像睡著了一般乒省。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上畦木,一...
    開封第一講書人閱讀 51,554評論 1 305
  • 那天袖扛,我揣著相機與錄音,去河邊找鬼。 笑死蛆封,一個胖子當(dāng)著我的面吹牛唇礁,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播惨篱,決...
    沈念sama閱讀 40,302評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼盏筐,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了砸讳?” 一聲冷哼從身側(cè)響起琢融,我...
    開封第一講書人閱讀 39,216評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎绣夺,沒想到半個月后吏奸,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,661評論 1 314
  • 正文 獨居荒郊野嶺守林人離奇死亡陶耍,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,851評論 3 336
  • 正文 我和宋清朗相戀三年奋蔚,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片烈钞。...
    茶點故事閱讀 39,977評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡泊碑,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出毯欣,到底是詐尸還是另有隱情馒过,我是刑警寧澤,帶...
    沈念sama閱讀 35,697評論 5 347
  • 正文 年R本政府宣布酗钞,位于F島的核電站腹忽,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏砚作。R本人自食惡果不足惜窘奏,卻給世界環(huán)境...
    茶點故事閱讀 41,306評論 3 330
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望葫录。 院中可真熱鬧着裹,春花似錦、人聲如沸米同。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,898評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽面粮。三九已至少孝,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間熬苍,已是汗流浹背韭山。 一陣腳步聲響...
    開封第一講書人閱讀 33,019評論 1 270
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留冷溃,地道東北人钱磅。 一個月前我還...
    沈念sama閱讀 48,138評論 3 370
  • 正文 我出身青樓,卻偏偏與公主長得像似枕,于是被迫代替她去往敵國和親盖淡。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 44,927評論 2 355

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