題目描述:
有 n 位乘客即將登機,飛機正好有 n 個座位。第一位乘客的票丟了,他隨便選了一個座位坐下。
剩下的乘客將會:
如果他們自己的座位還空着,就坐到自己的座位上,
當他們自己的座位被占用時,隨機選擇其他座位
第 n 位乘客坐在自己的座位上的概率是多少?
輸入當次飛機乘客總人數,輸出最后一名乘客坐在正確的座位上的概率。
解題思路:
(1)第一名乘客坐在自己的位置上的概率為1/n,第二名乘客坐在自己座位上概率也是1/n,此時,將第二名乘客作為第一名乘客,采取遞歸算法,算第n名乘客坐在自己座位上的概率。
結果:棧溢出。
分析原因:應該是輸入的乘客數量過大,導致java棧中不能容納。
思路改進:
將應用問題抽象成數學問題。
第一位乘客落座后,如果坐在自己的座位上,那最后一名乘客就一定能正確落座,如果第一位乘客沒有坐在自己的座位上,那假設其坐在乘客x的座位,本問題就轉化為以乘客x開始,求乘客n最終坐在自己位置上的概率。
不妨設當總人數為a是最后一名乘客坐在自己座位上的概率是f(a),那么總人數為n時,概率為f(n)。而問題經過轉化,第一個乘客坐到了第x個乘客的座位,輪到乘客x隨機坐了。那此時將乘客x視為新的乘客1,
易知f(n) = f(n-x)。即最終概率與人數無關。
這樣,經過遞歸,當人數總數 = 1時,f(1) = 1;而當n = 2,3,4……,f(n) = f(2) = 1/2;
就這樣,問題結束。當輸入的整數為1時,輸出為1。而當輸入的整數更多時,輸出為0.5.
代碼:
class Solution { public double nthPersonGetsNthSeat(int n) { return n == 1 ? n : 0.5; } }
最終結果:時間復雜度O(1),戰勝100%