HDU 1443 Joseph


Problem 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



约瑟夫环问题,可以从k+1~2k,2k+k+1~4k。。。因为第一个肯定要删除一个坏人。不断枚举,如果删除了一个好人,则该数不符合,continue,直到剩余人数为k。

经过实验,发现这个细节不用优化,即从i=k+1开始,一直++i,运行时间没有多大影响。

 1 #include<stdio.h>
 2 #include<iostream>
 3 #include<cstring>
 4
 5 using namespace std;
 6
 7 int ans[14]={0};
 8
 9 int joseph(int k)
10 {
11     int cnt,p;
12     if(ans[k])return ans[k];
13     for(int i=k+1;;i++)
14     {
15         for(cnt=2*k,p=0;cnt>k;cnt--)
16         {
17             p=(p+i-1)%cnt;
18             if(p<k)cnt=0;
19         }
20         if(cnt==k)
21         {
22             ans[k]=i;
23             return i;
24         }
25         if(i%(2*k)==0)
26         {
27             i+=k;
28         }
29     }
30     return 0;
31 }
32
33 int main()
34 {
35     int n;
36     while(scanf("%d",&n),n)
37     {
38         printf("%d\n",joseph(n));
39     }
40     return 0;
41 }


这里再给出原始问题的求解代码。

 1 /* 约瑟夫环问题 */
 2 # include <stdio.h>
 3 int main()
 4 {
 5     int m, n, i, s;
 6
 7     while (~scanf("%d%d", &m, &n))
 8     {
 9         s = 0;          // F1 = 0;
10         for (i = 2; i <= n; ++i)
11             s = (s + m) % i;
12         printf("%d\n", s+1);       // 原问题的编号是从1开始的
13     }
14
15     return 0;
16 }
时间: 2024-10-12 04:04:14

HDU 1443 Joseph的相关文章

poj 1012 &amp; hdu 1443 Joseph(约瑟夫环变形)

题目链接: POJ  1012: http://poj.org/problem?id=1012 HDU 1443: http://acm.hdu.edu.cn/showproblem.php?pid=1443 约瑟夫环(百度百科): http://baike.baidu.com/view/717633.htm?fr=aladdin Description The Joseph's problem is notoriously known. For those who are not famili

hdu 1443 Joseph (约瑟夫环)

Joseph Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submission(s): 2240    Accepted Submission(s): 1361 Problem Description The Joseph's problem is notoriously known. For those who are not familiar with the

(hdu step 2.2.2)Joseph(约瑟夫环变形问题)

题目: Joseph Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 2078 Accepted Submission(s): 1204   Problem Description The Joseph\\\\\\\'s problem is notoriously known. For those who are not familiar

转载:hdu 题目分类 (侵删)

转载:from http://blog.csdn.net/qq_28236309/article/details/47818349 基础题:1000.1001.1004.1005.1008.1012.1013.1014.1017.1019.1021.1028.1029. 1032.1037.1040.1048.1056.1058.1061.1070.1076.1089.1090.1091.1092.1093. 1094.1095.1096.1097.1098.1106.1108.1157.116

HDU 2516 取石子游戏(巴什博弈)

取石子游戏 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 2524    Accepted Submission(s): 1443 Problem Description 1堆石子有n个,两人轮流取.先取者第1次可以取任意多个,但不能全部取完.以后每次取的石子数不能超过上次取子数的2倍.取完者胜.先取者负输出"Second win&q

HDU 6203 ping ping ping [LCA,贪心,DFS序,BIT(树状数组)]

题目链接:[http://acm.hdu.edu.cn/showproblem.php?pid=6203] 题意 :给出一棵树,如果(a,b)路径上有坏点,那么(a,b)之间不联通,给出一些不联通的点对,然后判断最少有多少个坏点. 题解 :求每个点对的LCA,然后根据LCA的深度排序.从LCA最深的点对开始,如果a或者b点已经有点被标记了,那么continue,否者标记(a,b)LCA的子树每个顶点加1. #include<Bits/stdc++.h> using namespace std;

HDU 5542 The Battle of Chibi dp+树状数组

题目:http://acm.hdu.edu.cn/showproblem.php?pid=5542 题意:给你n个数,求其中上升子序列长度为m的个数 可以考虑用dp[i][j]表示以a[i]结尾的长度为j的上升子序列有多少 裸的dp是o(n2m) 所以需要优化 我们可以发现dp的第3维是找比它小的数,那么就可以用树状数组来找 这样就可以降低复杂度 #include<iostream> #include<cstdio> #include<cstring> #include

hdu 1207 汉诺塔II (DP+递推)

汉诺塔II Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submission(s): 4529    Accepted Submission(s): 2231 Problem Description 经典的汉诺塔问题经常作为一个递归的经典例题存在.可能有人并不知道汉诺塔问题的典故.汉诺塔来源于印度传说的一个故事,上帝创造世界时作了三根金刚石柱子,在一根柱子上从下往

[hdu 2102]bfs+注意INF

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2102 感觉这个题非常水,结果一直WA,最后发现居然是0x3f3f3f3f不够大导致的--把INF改成INF+INF就过了. #include<bits/stdc++.h> using namespace std; bool vis[2][15][15]; char s[2][15][15]; const int INF=0x3f3f3f3f; const int fx[]={0,0,1,-1};