约瑟夫问题
有n个人围成一圈,从第k个人开始从一报数,报到m的这个人被淘汰,然后第m + 1个人继续从1开始报数… 问最后留下第几个人,且写出被淘汰的过程。
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
//定义顺序表
typedef struct{
int *elem;
int length;
int maxlength;
}SqList;
bool InitList(SqList *L,int size){ //数据表的创建
L->maxlength = size;
L->elem = (int *)malloc(sizeof(SqList) * size); //给顺序表创建动态空间
if (!L->elem){
return false;
}
L->length = 0;
return true;
}
int main()
{
int n;
int m;
int k;
//输入且验证合理性
printf("请输入总人数:\n");
scanf("%d", &n);
while(n < 1) {
printf("人数不能小于1,请重新输入:");
scanf("%d", &n);
}
printf("输入每隔多少淘汰一个人:\n");
scanf("%d", &m);
while(m < 1 || m > n) {
printf("范围必须在1到n之间,请重新输入:");
scanf("%d", &m);
}
printf("请输入从第几个人开始报数:\n");
scanf("%d", &k);
while(k < 1 || k > n) {
printf("范围必须在1到n之间,请重新输入:");
scanf("%d", &k);
}
//初始化参数
SqList L;
bool isSuccess = InitList(&L, n);//创建表
if(!isSuccess) {
printf("创建顺序表失败,程序停止运行\n");
return;
}
int i;
for(i = 0; i < L.maxlength; i ++) {//为表赋值
L.elem[i] = 1;
L.length ++;
}
printf("\n准备报数!\n\n");
//方法执行
int j = 1;
for(i = k - 1; L.length > 1; i ++) {
if(!L.elem[i%n]) continue;//为0则跳过
if(j == m) {
j = 1;
L.elem[i%n] = 0;
printf("第%d个人被淘汰!\n",(i%n)+1);
L.length --;
}
else j ++;
}
for(i = 0;i < n;i++)if(L.elem[i])break;
printf("\n最终留下了第%d个人!\n",i+1);
//释放内存
free(&L);
L.elem = NULL;
system("pause");
return 0;
}