(学习笔记)链表解决约瑟夫环的Java实现

本文详细解析了约瑟夫环问题,通过链表实现算法,展示了如何在N个人的环形队伍中,找到特定条件下最后存活的M-1个人的编号。提供了完整的代码示例及运行结果。

约瑟夫环问题描述

N个人排成圈,从1-N编号。从1号开始报数,每次报M的人自杀。下一人重新从一号开始报数,依然是报M的人自杀。问最后存活下来的M-1人的编号。(M<N)

解题思路

  • 创建一个链表s,添加1-N个人的编号,设i为要自杀的人的下标
  • 则第一名自杀者的下标i为M-1,s移出该节点。此时链表M-N节点前移一位。
  • 计算第二位自杀者下标为i=i(上一次:i=M-1)+M-1,为了实现按环循环删除,对上式取模。i=(i+M-1)%(此时链表的长度)
  • 重复上述过程,直到链表最后长度等于M-1.

代码实现

public class Joseph{
    //输出每次自杀者的编号
	public static void suicide(List<Integer> s,int M){
		int i=M-1;
		while(s.size()>M-1){
			System.out.println("自杀者编号:"+s.get(i));
			s.remove(i);
			i=(i+M-1)%s.size;
		}
	}
	public static void main(String[] args){
		ArrayList<Integer> s=new ArrayList<Integer>();
		int k=3;//报3的人自杀,所以最后剩余2人
		//向链表中加入41人
		for(int i=1;i<42;i++){
			s.add(i);
		}
		suicide(s,k);
		//输出链表中剩余两人的编号
		System.out.println("存活下来的"+(k-1)+“人的编号:”)
		s.forEach(System.out::println);
	}
} 

运行结果

在这里插入图片描述

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值