您的位置:首页 > 其它

POJ1012 Joseph

2017-10-12 22:38 274 查看
原题:

Description
The Joseph's problem is notoriously known. For those who are not familiar with the original problem: from among n people, numbered 1, 2, . . ., n, standing
in circle every mth is going to be executed and only the life of the last remaining person will be saved. Joseph was smart enough to choose the position of the last remaining person, thus saving his life to give us the message about the incident. For example
when n = 6 and m = 5 then the people will be executed in the order 5, 4, 6, 2, 3 and 1 will be saved. 

Suppose that there are k good guys and k bad guys. In the circle the first k are good guys and the last k bad guys. You have to determine such minimal m that all the bad guys will be executed before the first good guy. 

Input
The input file consists of separate lines containing k. The last line in the input file contains 0. You can suppose that 0 < k < 14.
Output
The output file will consist of separate lines containing m corresponding to k in the input file.
Sample Input
3
4
0

Sample Output
5
30


题目大意:
类似与约瑟夫环,总共2k个人,要求求最小的m(即报数为k的人淘汰),使后面k个人先被淘汰



分析:

*要使前k个人不被淘汰,应有m>k

*从每一次分析,s为第i-1轮被淘汰的人的下标,则第i轮淘汰的人的下标为(m-1+i)%(2*k-i)

*存储结果,防止超时

代码:
#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
int a[15]; // store the result
int main(){
int k,m;
memset(a,0,sizeof(a)); //initialize a with 0
while(scanf("%d",&k) && k!=0){
if(a[k]){ //determine whether we had calculated the corresponding result of k
printf("%d\n",a[k]);
continue;
}
for(m=k;;m++){ //start from m, increase progressively
int i=0,s=0; //s:the index of the person to kill, i: the time
while(i<2*k){
s=(m-1+s)%(2*k-i);
if(s<k) //when the person to kill is good guy
break;
i++;
}
if(i>=k)
break;
}
a[k]=m;
printf("%d\n",a[k]);
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: