约瑟夫问题的解决
问题概述
有n个人,编号为1~n,从k个人开始报数,从1开始报,报到m的人会死掉,然后从第m+1个人开始,重复以上过程。在死了n-1个人后,问最后一个人的编号是?
package learn;
/**
* 单向环形列表
* 直接使用前边定义的链表和节点了,
*/
public class CircleLinkList {
public static void domethod(int num,int k,int m){
if(k>num){
return;
}
LinkList linkList = new LinkList();
Node temp=linkList.head;
for(int i=1;i<=num;i++){
linkList.add(new Node(i));
temp=temp.next;//最终时尾节点
}
// linkList.list();
Node first = linkList.head.next;//第一个人,编号为一
// System.out.println(first);
temp.next=first;//写了这么多就是想让形成一个链表
// linkList.list();//再使用这个会一直遍历
// Node tempnode;
while (first.data!=k){
first=first.next;//找到第K个人
temp = temp.next;
}
// System.out.println("=========");
// System.out.println(first);
// System.out.println(temp);
int i=1;//从一开始报数。
while (true){
if(temp.next==first&&first.next==temp){
if(m%2==0){
System.out.println("========");
System.out.println(temp);
System.out.println(first);
}
else{
System.out.println("*********");
System.out.println(first);
System.out.println(temp);
}
break;
}
if(i==m){
temp.next=first.next;
System.out.println(first);
first=temp.next;
i=1;
}
else{
i++;
first=first.next;
temp=temp.next;
}
}
}
public static void main(String[] args) {
CircleLinkList.domethod(5,3,2);
}
}
重点思路在于剩下俩人的时候怎么办,想了一个办法,此时,i=1,就剩下first和temp两个元素,而first所指的元素,此时时i,直接m单数时first,双数时temp输出即可!