您的位置:首页 > 理论基础 > 数据结构算法

数据结构与算法(4、约瑟夫环问题到循环链表)

2015-07-21 21:52 323 查看
首先先解释约瑟夫环问题,这个问题,背景其实挺残酷的,来自于一场自杀游戏,举个现实的例子,如果你有4个朋友,但是只能给一个人带饭,那么做这样的游戏,4个人围成一个环,你说从1开始数,数到2,就淘汰掉2,剩下的继续围成一个环,在继续这个游戏,直到剩下一个为止。

表达能力有限,直接百度百科!

约瑟夫环(约瑟夫问题)是一个数学的应用问题:已知n个人(以编号1,2,3…n分别表示)围坐在一张圆桌周围。从编号为k的人开始报数,数到m的那个人出列;他的下一个人又从1开始报数,数到m的那个人又出列;依此规律重复下去,直到圆桌周围的人全部出列。通常解决这类问题时我们把编号从0~n-1,最后结果+1即为原问题的解。

那么如何构建环以及如何进行删除操作是最重要的了!

构建之前,我们要有一个已经存在的tail,有无数据不重要,


首先是构建的问题:

//实现一个插入操作
void addElements(int value){
if(tail==nullptr){
//第一种情况是链表里面没有任何的结点,那么新建的结点有特殊的操作,指向自己,形成一个环
tail=new node(value);
//让tail指向自己,形成一个小环
tail->next=tail;
}else{
//新建结点
node * new_node=new node(value);
//让原来的结点的next指向变成此时新结点的指向
new_node->next=tail->next;
//让tail指向新结点,形成一个环
tail->next=new_node;
//让新结点成为tail,继续进行下一步的增加操作,循环往复
tail=new_node;
}
}


构建完约瑟夫之后,接下来是一个删除操作

/*index表示需要输入的数*/
void delete(index){
//设置临时变量
node*p=tail;
//避免程序抛出nullPointexception
if(p!=nullptr&&p->next!=p){
for(int i=0;i<index-1;i++){
p=p->next;
}
}
node * delete_element=p->next;
p->next=p->next->next;
if(delete_element==tail)
tail=p;
//C++实现,需要释放内存
delete delete_element;
}


如此就可以实现一个约瑟夫环的构建与删除的问题,总结一下:

1、在构建的时候,首先意识到这个是一个圆环,所以哪怕是一个元素,也要让它指向自己。

2、在构建新结点的时候,需要让tail原本的关系给新结点,然后再指向新结点,不可以颠倒顺序,不然会丢失原结点的关系

从约瑟夫环衍生到循环链表,其实约瑟夫环就是一个循环链表,哈哈哈
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: