題目
一群猴子排成一圈氮墨,按1,2,…,n依次編號溶褪。然后從第1只開始數(shù)肮疗,數(shù)到第m只,把它踢出圈漱抓,從它后面再開始數(shù),再數(shù)到第m只精钮,在把它踢出去…威鹿,如此不停的進行下去,直到最后只剩下一只猴子為止杂拨,那只猴子就叫做大王专普。要求編程模擬此過程,輸入m弹沽、n, 輸出最后那個大王的編號檀夹。用程序模擬該過程。
該題目本質(zhì)是約瑟夫環(huán)的考察策橘,算法還有一個起源故事炸渡,據(jù)說著名猶太歷史學家約瑟夫在羅馬人占領(lǐng)喬塔帕特后,39 個猶太人與約瑟夫及他的朋友躲到一個洞中丽已,39 個猶太人決定寧愿死也不要被敵人抓到蚌堵,于是決定了一個自殺方式,41 個人排成一個圓圈沛婴,由第1個人開始報數(shù)吼畏,每報數(shù)到第 3 人該人就必須自殺,然后再由下一個重新報數(shù)嘁灯,直到所有人都自殺身亡為止泻蚊。由于約瑟夫和他的朋友并不想自殺,但又無法反抗丑婿,只能同意了這個方式性雄,但他把自己和朋友分別安排在了 16 和 31 這兩個位置没卸,最后順利活到了最后。
以上故事再次驗證了秒旋,學好數(shù)理化约计,走遍天下都不怕!
代碼實例
<?php
/**
* @param $n int 元素總個數(shù)
* @param $m int 指定序數(shù)
* @return mixed
*/
function mk($n, $m)
{
//根據(jù)總數(shù)生成數(shù)組
$range = range(1, $n);
$i = 1;
while (count($range) > 1) {
//如果不是當前元素迁筛,壓入數(shù)組末尾并刪除當前下標
if ($i % $m != 0) array_push($range, $range[$i - 1]);
unset($range[$i - 1]);
$i++;
}
return $range[$i - 1];
}
用以上函數(shù)來驗證故事煤蚌,修改一下函數(shù)體邏輯即可
<?php
/**
* @param $n int 元素總個數(shù)
* @param $m int 指定序數(shù)
* @return mixed
*/
function mk($n, $m)
{
//根據(jù)總數(shù)生成數(shù)組
$range = range(1, $n);
$i = 1;
//驗證最后剩下的兩個元素
while (count($range) > 2) {
//如果不是當前元素,壓入數(shù)組末尾并刪除當前下標
if ($i % $m != 0) array_push($range, $range[$i - 1]);
unset($range[$i - 1]);
$i++;
}
return $range;
}
$survivor = mk(41, 3);
print_r($survivor); //16,31