【经典算法】约瑟夫环

约瑟夫环算法(循环链表解决)
问题:约瑟夫环
 有编号从1到N的N个人坐成一圈报数,报到M的人出局,下一位再从1开始,
 如此持续,直止剩下一位为止,报告此人的编号X。输入N,M,求出X。


(每次递增1个数)

public class Josephus {
    public static void main(String[] args) {
        System.out.println("Input N and M.");
        Scanner s = new Scanner(System.in);
        int n = s.nextInt();
        int m = s.nextInt();
        int point=0,number=1;
        List<Integer> list = new ArrayList<Integer>();
        for(int i=1;i<=n; i++){
            //初始化链表
            list.add(i);
        }

        while(list.size()>1){
            if(number%m==0){
		System.out.println(list.get(point));  
                list.remove(point);
                --point;
            }
            ++point;//指针后移
            ++number;
            if(point>list.size()-1){
                //指针越界重新开始
                point=0;
            }
        }
        

        System.out.println(list.get(0));
        
    }
}



另一种实现方式:(每次递增3个数)

public class Yue {
	public static void main(String[] args) {  
		         Scanner scanner = new Scanner(System.in);  
		         System.out.print("请输入总人数:");  
		         int totalNum = scanner.nextInt();  
		         System.out.print("请输入报数的大小:");  
		         int cycleNum = scanner.nextInt();  
		         yuesefu(totalNum, cycleNum);  
		     }  
		   
		    public static void yuesefu(int totalNum, int countNum) {  
		         // 初始化人数  
		         List<Integer> start = new ArrayList<Integer>();  
		         for (int i = 1; i <= totalNum; i++) {  
	             start.add(i);  
		         }  
		         //从第K个开始计数  
		        int k = 0;  
		         while (start.size() >0) {  
		             k = k + countNum;  
		             //k表示在当前链表中第m人的索引位置
		            k = k % (start.size()) - 1;  
		            // 判断是否到队尾  
		             if (k < 0) {  
		                 System.out.println(start.get(start.size()-1));  
		                 start.remove(start.size() - 1);  
		                 k = 0;  //重置索引位置到第一个
		             } else {  
		                 System.out.println(start.get(k));  
		                 start.remove(k);  
		             }  
		         }  
		     }  
}


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值