約瑟夫問題
時間限制(普通/Java) : 1000 MS/ 3000 MS 運作記憶體限制 : 65536 KByte
總送出 : 253 測試通過 : 37
比賽描述
17世紀的法國數學家加斯帕在《數目的遊戲問題》中講的一個故事:15個教徒和15 個非教徒在深海上遇險,必須将一半的人投入海中,其餘的人才能幸免于難,于是想了一個辦法:30個人圍成一圓圈,從第一個人開始依次報數,每數到第九個人就将他扔入大海,如此循環進行直到僅餘15個人為止。問怎樣排法,才能使每次投入大海的都是非教徒。這個故事的問題是經典的約瑟夫問題。
現在我們知道有n個教徒和非教徒,其中非教徒數為m,将他(她)們按從1到n的次序放置到圓圈中,報數為k,要将所有非教徒投入大海,請按遞增次序給出非教徒在圓圈中的次序。
輸入
每行是用空格分開的三個整數,第一個是 n, 第二個是 m,第三個是k ( 0 <= m<n <=100,0 <k <=100)。最後一行是:
0 0 0
輸出
對于每個測試用例,輸出一行,依次包含:
l “Case #:”,#表示用例序号。
l m個非教徒在圓圈中的次序,以空格分隔;如沒有非教徒,則無需輸出。
樣例輸入
6 2 9
12 4 8
8 3 2
0 0 0
樣例輸出
Case 1: 1 3
Case 2: 1 4 8 11
Case 3: 2 4 6
提示
題目來源
NUPT
/* Wrong Answer at Test 2
#include<iostream>
int main(){
bool drop[101];
int n,m,k,i,j,cas=0;
while(scanf("%d%d%d",&n,&m,&k)==3 && n){
cas++;
printf("Case %d:",cas);
if(!m){
printf("\n");
continue;
}
memset(drop,0,sizeof(drop));
i = 0;
while(m--){
j = k;
while(j){
i = (i+1)%n;
if(!drop[i]){
j--;
}
}
drop[i] = 1;
}
for(i=0;i<n;i++){
if(drop[i]){
printf(" %d",i);
}
}
printf("\n");
}
}
*/
#include<iostream>
int main(){
bool drop[101];
int n,m,k,i,j,cas=0;
while(scanf("%d%d%d",&n,&m,&k)==3 && n){
cas++;
printf("Case %d:",cas);
if(!m){
printf("\n");
continue;
}
memset(drop,0,sizeof(drop));
i = -1; //WA2
while(m--){
j = k;
while(j){
i = (i+1)%n;
if(!drop[i]){
j--;
}
}
drop[i] = 1;
}
for(i=0;i<n;i++){
if(drop[i]){
printf(" %d",i+1);
}
}
printf("\n");
}
}