链表实现约瑟夫环问题

2约瑟夫环(综合性实验)

问题描述

约瑟夫问题的一种描述是,编号为1, 2, …, n的n个人按顺时针方向围坐一圈,每人持有一个密码(正整数)。一开始任选一个正整数作为报数上限值m,从第一个人开始按顺时针方向自1开始顺序报数,报到m时停止报数。报m的人出列,将他的密码作为新的m值,位于他顺时针方向上的下一个人开始重新从1报数,如此下去,直至所有人全部出列。试设计一个程序求出出列顺序。

基本要求

利用单向循环链表存储结构模拟此过程,按照出列的顺序打印出每个人的编号。

测试数据

m的初值为20,密码分别为3、1、7、2、4、8和4(正确的结果应为6、1、4、7、2、3和5)。

实现提示

程序运行后首先要求用户指定初始报数上限值,然后读取每个人的密码(设n≤30)。

本题可使用模板类LinkList,也可使用STLList容器。

注:当时控制台对齐效果做的不好,哈哈!



【MoshowMenu.h】自制简易菜单v1.02

#include <iostream>
using namespace std;

//②〇①〇〇③〇④〇③〇⑤④  10软开B(郑锴) 自制简易菜单!
//v1.02<2011.10.09>
//●AddMenu传参由string xxx改为char xxx[],防止vs2010上通过而vs2008报错
//●Choise增加输入缓冲区清楚机制,防止输入"\&~"等字符导致程序卡死
//

void MainMenu()
	{
		system("Color 2E");
		system("Title 10软开B(郑锴)");
		cout<<"\n\n\n\n\t\t ★★姓名→郑锴★★★学号→xxxxxxxxxxx ★★\n"
			<<"\t \t ***Warning:Don't Ctrl+C Copy Me!Copy必究*** \n  \n";
	}

void AddMenu(char xxx[])
	{
		cout<<"\t\t\t\t●"<<xxx<<endl;
	}

int Choise()
{
	int choise;
	cout<<"\n\n\t\t请输入选项:";
	cin>>choise;
	cin.clear();
	cin.sync(); 
	system("cls");
	return choise;
}

//应用实例:
//void main()
//{
//	int open=1;
//	xxxx<int> x;
//	while(open)
//	{
//		MainMenu();
//		AddMenu("*.初始化x");
//		AddMenu("0.退出程序");
//		AddMenu("1.__n____");
//		AddMenu("2._______");
//		switch(Choise())
//		{
//			case 0:
//				open=0;
//				cout<<"程序即将退出!"<<endl;
//				break;	
//			case 1:
//				int n;
//				cout<<"输入n:"
//				x.xxxx(n);
//				break;
//			case 2:
//				x.xxxx();
//				break;
//			default:
//				cout<<"输入错误!"<<endl;
//				break;
//		}
//	}
//	system("pause");
//}

【InitList.h】//自制的链表类
#include<iostream>
using namespace std;

class Node //链表
{
public:
	int data;
	Node *next;
};

Node *initList(int n)  //函数:生成链表存放数据
{
	Node *list = new Node;
	Node *p = list;

	p->data = 1;
	p->next = 0;

	for (int i = 2; i <= n; i++)
	{
		Node *temp = new Node;
		temp->data = i;
		temp->next = 0;

		p->next = temp;
		p = temp;
	}

	p->next = list;
	return list;
}

void Print(Node *list)  //函数:打印链表
{
	if (list)
	{
		Node *p = list;
		cout<<p->data;
		while (p->next != list)
		{
			p = p->next;
			cout<<"→"<<p->data;
		}
	}
	cout<<endl;
}

【moshowmain.cpp】主函数
#include"InitList.h"
#include"MoshowMenu.h"

void main() //Moshow魔手.郑锴
{
	int n;
	int m[20];

	//入座
	MainMenu();
	AddMenu("请输入围坐一圈的人数n:");
	cin>>n;
	Node *mylist = initList(n);

	//给编号!
	AddMenu("初始编号是:");
	Print(mylist);

	//初始化密码!
	AddMenu("请输入初始密码m:");
	cin>>m[0];
	for (int i = 1; i <= n; i++)
	{
		cout<<"请输入第"<<i<<"个人的密码:";
		cin>>m[i];
	}

	//逐个按顺序出列!
	AddMenu("出列顺序是: ");
	int j = 0;
	Node *p = mylist;
	Node *t = new Node;
	while( p->next != p)
	{
		for(int k = 1 ; k < m[j] ; k++ )
		{
			t = p;
			p = p->next;
		}
		cout<<p->data<<"→";
		j = p->data;       
		t->next = p->next;
		delete p;
		p = t->next;
	}
	cout<<p->data<<"#end! \n"; //不要忘记还有最后一个人
	system("pause");
}


已标记关键词 清除标记
相关推荐
©️2020 CSDN 皮肤主题: 博客之星2020 设计师:CY__ 返回首页