报数游戏
问题描述:设有N个人围坐一圈并按顺时针方向从1到N编号,从第S个人开始进行1到M报数,报数到第M 个人时,此人出圈,再从他的下一个人重新开始1到M的报数,如此进行下去直到所有的人都出圈为止。现要打印出出圈次序。
要求实现函数:
void circle_sort (int n, int s, int m, int *p)
输入:n 游戏总人数 s 报数的起始编号 m 报数的数值
输出:p 指向长度为n的数组,出圈次序保存在p指向的数组中
问题描述:设有N个人围坐一圈并按顺时针方向从1到N编号,从第S个人开始进行1到M报数,报数到第M 个人时,此人出圈,再从他的下一个人重新开始1到M的报数,如此进行下去直到所有的人都出圈为止。现要打印出出圈次序。
要求实现函数:
void circle_sort (int n, int s, int m, int *p)
输入:n 游戏总人数 s 报数的起始编号 m 报数的数值
输出:p 指向长度为n的数组,出圈次序保存在p指向的数组中
示例:n=7 s=2 m=3 出圈次序为:4 7 3 1 6 2 5
#include <iostream>
using namespace std;
void circle_sort(int n, int s, int m, int *p );
void add1(int n, int &count , int *a);//实现下一位报数功能
int main()
{
int i, n, s, m;
cout << "Please input the number of people (n):";
cin>>n;
cout<<endl;
cout << "Please input the start number (s):";
cin>>s;
cout<<endl;
cout << "Please input the circle number (m):";
cin>>m;
cout<<endl;
int array[n];
for(i = 0; i < n; i++)
{
array[i] = 0;
}
circle_sort(n, s, m, array);
for(i = 0; i < n; i++)
{
cout<<array[i];
cout<<"\t";
}
cout<<endl;
return 0;
}
void circle_sort(int n, int s, int m, int *p )
{
if(n < 1 || s > n || s < 1 || m < 1)
return ;
int number = 1 ,i;
int count = s;
int array[n+1]; //用数组array[]存放所有的序号
for(i = 0; i < n+1; i++)//将数组中的每个元素初始化为相应的序号
{
array[i] = i;
}
while(number != n+1) //报数,直到n个人全部被点出来
{
i = 1;
if(number != 1) //如果不是第一次开始报数,每新一轮从下一位开始计数
add1(n, count, array);
while(i != m) //报数1~m,出来一个
{
add1(n, count, array);
i++;
}
p[number-1] = array[count];//找到新一轮要被删除的序号,保存在输出数组p[]
array[count] = 0;
number++;
}
}
void add1(int n, int &count , int *array)
{
if(count == n) //如果到达数组尾,重新返回到array[1]
count = 1;
else
count++;
while(array[count] == 0)//跳过已经出去的序号
{
if(count == n) //如果到达数组尾,重新返回到array[1]
count = 1;
else
count++;
}
}
———————————————————————————————————————————————————————————————————————————
2014/04/04 22:05
这实际上是Josephus问题,用循环链表比用数组要高效得多。
struct node{ //定义链表结点结构
int elem;
node *next;
node(int x, node* t)
{
elem = x;
next = t;
}
};
typedef node* link;
void Josephus(int n, int s, int m)
{
int i = 0;
link head = new node(1,NULL);
//head->next = head;
link x = head;
link p = NULL;
for( i= 2; i <= n; i++)
{
x = (x->next = new node(i,NULL));
}
x->next = head;
i = 1;
x = head;
while(i != s)
{
x = x->next;
i++;
}
while(x != x->next)
{
for(i = 1; i < m-1; i++ )
x = x->next;
p = x->next;
x->next = p->next;
x = x->next;
cout<<p->elem<<"\t";
delete p;
}
cout<<x->elem<<"\t";
delete x;
head = NULL;
}