KMP演算法與乙個經典概率問題

2021-06-28 18:40:18 字數 2290 閱讀 1488

考慮乙個事件,它有兩種概率均等的結果。比如擲硬幣,出現正面和反面的機會是相等的。現在我們希望知道,如果我不斷拋擲硬幣,需要多長時間才能得到乙個特定的序列。

序列一:反面、正面、反面

序列二:反面、正面、正面

首先,我反覆拋擲硬幣,直到最近的三次拋擲結果形成序列一,然後我記下這次我拋擲了多少次才得到了我要的序列。重複執行這個過程,我可以算出得到序列一平均需要的拋擲次數。同樣地,反覆拋擲硬幣直到序列二產生,它所需要的次數也有乙個平均值。你認為這兩個平均值哪乙個大哪乙個小?換句話說,出現序列一平均所需的拋擲次數少還是出現序列二平均需要的次數少?

大多數人會認為,兩個序列會以同樣快的速度出現,因為在所有「正」和「反」的8種三元組合裡,「反正反」和「反正正」各佔1/8,其概率是均等的。而事實上,我們將會看到擲出序列二所需的次數更少一些。不妨考慮這樣乙個問題:在由「正」和「反」構成的n位01序列中,有多少個序列以序列一結尾但之前不曾出現過序列一?有多少個序列以序列二結尾但之前不曾出現過序列二?當n比較小時,兩者答案是一樣的(例如n=3時符合要求的情況都是唯一的),但到後來n越大時,兩者的差距越明顯:後者的個數總比前者的個數要多一些。不妨看一看n=6的情況。對於序列一,只有以下5個序列是符合要求的:

但對於序列二來說,符合條件的序列就有7個:

你可以通過計算機程式設計列舉,計算一下n為其它值的情況。計算結果和剛才也一樣:在n位01序列中,以序列二結尾但之前不含序列二的情況不會少於以序列一結尾但之前不含序列一的情況。這說明,拋擲第n次硬幣後恰好出現了序列二,其概率不會小於恰好出現序列一的概率。顯然,當n漸漸增大時,這個概率應該呈下降趨勢;同時,隨著n的增長,兩個序列各自出現的概率由相等開始慢慢拉開差距,第n次拋擲產生序列二的概率下降得要緩慢一些,或者說更多的情況集中發生在n更小的時候。因此總的來說,出現序列二所需要的拋擲硬幣次數的期望值更小。

雖然我們通過一系列的觀察驗證了這個結論,並且我們也相信這個結論是正確的(雖然沒有嚴格的證明),但我們仍然不是很接受這個結論。這種情況是有悖於我們的直覺的,它與我們的生活經驗不相符合。此刻,我們迫切需要乙個解釋,來說明這種出人意料的反常現象產生的原因。

如果不親自做幾次試驗的話,你很難體會到這種微妙的差距。考慮整個遊戲的實際過程,「反正正」序列顯然會出現得更早一些。假如某一次我們得到了序列「反正」。如果我們需要的是「反正反」序列,那麼下一次拋擲結果為反面將結束本輪的拋擲,而下一次是正面則前功盡棄,你必須再次從零開始。如果我們需要的是「反正正」序列,那麼下一次拋擲結果為正面將結束本輪的拋擲,而下一次是反面的話我至少不會慘到一切歸零,這相當於我已經有了乙個反面作為新的開頭,只需再來兩個正面即可。這樣看的話,提前擲出「反正正」的可能性更大一些。

反覆體會上面的想法,了解kmp演算法網友會恍然大悟:這就是kmp演算法的基本思路!考慮這樣乙個問題:我們在當前字串中尋找子串「反正正」第一次出現的位置。假如當前已經能匹配模式串的前兩個字「反正」,主串中的下乙個字是「正」則匹配成功,主串的下乙個字是「反」則將使模式串的當前匹配位置退到第乙個字。考慮乙個更複雜的例子:我們希望在主串中尋找子串abbaba,現在已經在主串中找到了abbab。如果主串下乙個字元是a,則成功匹配;如果主串下乙個字元是b,則模式串最多能匹配到的位置退到了第三個字元,我只需要從abb開始繼續匹配,而不必一切從頭再來。

我們可以用kmp演算法完美地解決上面的問題。(kmp演算法的**摘自我之前的博文)

首先我們構造兩個模式串010和011,分別代表投擲硬幣中的反正反和反正正(0代表反,1代表正)。然後再構造n位的所有2進製數排列(代表所有可能出現的硬幣正反面組合)作為主串。然後定義兩個計數量,通過kmp演算法進行主串和模式串的匹配,010分別與所有的二進位制數進行匹配,匹配成功一次計數量1加一,統計出010的總共匹配成功次數。同理,統計011的總共匹配成功次數。然後比較兩個計數量的大小,即可得到我們想要的結論:到底反正反和反正正哪個更容易出現。

#include#includeusing namespace std;

void getnext(char *p,int *next)//p為模式串

我們可以看到,隨著投擲次數的增加,反正正的序列開始大於反正反的序列,且隨著n的增加,兩者的差距越來越大。

KMP演算法與乙個經典概率問題

考慮乙個事件,它有兩種概率均等的結果。比如擲硬幣,出現正面和反面的機會是相等的。現在我們希望知道,如果我不斷拋擲硬幣,需要多長時間才能得到乙個特定的序列。序列一 反面 正面 反面 序列二 反面 正面 正面 首先,我反覆拋擲硬幣,直到最近的三次拋擲結果形成序列一,然後我記下這次我拋擲了多少次才得到了我...

KMP演算法與乙個經典概率問題

考慮乙個事件,它有兩種概率均等的結果。比如擲硬幣,出現正面和反面的機會是相等的。現在我們希望知道,如果我不斷拋擲硬幣,需要多長時間才能得到乙個特定的序列。序列一 反面 正面 反面 序列二 反面 正面 正面 首先,我反覆拋擲硬幣,直到最近的三次拋擲結果形成序列一,然後我記下這次我拋擲了多少次才得到了我...

乙個概率問題

有三個盒子,其中乙個盒子裡面是大獎,另外兩個盒子是空的,你選中其中乙個,在你開啟這個盒子之前,主持人開啟了剩下兩個盒子當中的乙個,空的。2018 8 3 9 25更新,由於頭天晚上憑藉記憶手打,此處描述有不嚴謹,在此更新 主持人知道哪乙個盒子裡面有大獎,開啟了必定空的乙個盒子。問,你是繼續堅持一開始...