问题就不在描述了,就是那几个人围成一桌,出来一个又一个。。。
我的思路
1、结构体为:
struct node
{
int id;
int passwd;
struct node *next;
}
2、输入人数,创建单循环链表;
3、显示所有人的信息;
4、根据规则删除队伍中的人:根据初始密码,采用循环,判断要删除的节点信息。
下面给出源代码:
#include<stdio.h>
#include<stdlib.h>
#define MAX 100
typedef struct node
{
int id;
int passwd;
struct node *next;
}Node;
Node *CreatJoseph(int n)
{
printf("*****创建约瑟夫环*****\n");
int i,x;
Node *head,*one,*two;
head = (Node *)malloc(sizeof(struct node));
printf("请输入第1个人的密码:");
scanf("%d",&x);
head->id = 1;
head->passwd = x;
head->next = NULL;
two = head;
two->next = head;
for(i = 2; i<=n; i++)
{
one = (Node *)malloc(sizeof(struct node));
printf("请输入第%d个人的密码:",i);
scanf("%d",&x);
one->id = i;
one->passwd = x;
one->next = head;
two->next = one;
two = one;
}
return head;
}
void Print(Node *head,int n)
{
printf("*****打印约瑟夫环*****\n");
int i;
Node *p;
p = head;
for(i = 0; i<n; i++)
{
printf("第%d个人的密码是%d \n",p->id,p->passwd);
p=p->next;
}
}
void Joseph(Node *head)
{
printf("*****约瑟夫出局顺序*****\n");
int i,passwd;
Node * one ,* two, *del;
one = two = head;
while(two->next!=head)
{
two = two->next;
}
printf("请输入原始密码:");
scanf("%d",&passwd);
while(1)
{
for(i = 1; i<passwd; i++)
{
two = one;
one = one->next;
}
if(one == two) break;
del = one;
two->next = del->next;//此时del和one指向相同
one = one->next;
printf("出局人的编号是%d,密码是%d.\n",del->id,del->passwd);
passwd = del->passwd;
free(del);
}
printf("最后剩下的人的编号是%d,密码是%d.\n",one->id,one->passwd);
}
int main()
{
int n;
printf("请输入总人数(最大是%d):",MAX);
scanf("%d",&n);
Node * head = (Node *)malloc(sizeof(struct node));
head->next = NULL;
head = CreatJoseph(n);
Print(head,n);
Joseph(head);
}