3,java数据结构和算法:约瑟夫环出队顺序, 单向环形链表的应用
什么是约瑟夫环? 就是数小孩游戏:


直接上代码: 要实现这个,只需要理清思路就好了
孩子节点:
class Boy{
int no;//当前孩子的编码
Boy next; // 下一节点
public Boy(int no) {
this.no = no;
}
public Boy(int no, Boy next) {
this.no = no;
this.next = next;
}
@Override
public String toString() {
return "Boy{" +
"no=" + no +
'}';
}
}
单向环形链表:
//约瑟夫环, 单向环状链表
class SingleCircleLinkList{
//1,先造一个first指针,为null, 用来指向第一个小孩, 永远不会变
//2, 创建一个 curBoy指针,当只有一个小孩时候,curBoy指向第一个小孩,
// 当有n个小孩时, curBoy永远指向当前的小孩, 这样的好处是便于遍历
Boy first = null;
int boyCount;
/**
* 根据 n 个数创建 约瑟夫环
* @param n
*/
public void creatYosepfuCircle(int n){
//思路: 1,创建一个first指针, 用来指向第一个节点,永远不会变
// 2, 创建一个curBoy指针, 用来指向当前节点, 当只有一个节点时,first 和curBoy都指向这个节点,
// 当有多个节点时候, first指向第一个节点, curBoy指向最后一个节点, 用来遍历使用?
Boy curBoy = null;//curBoy指针,用来指向当前节点,
if (n < 1) {
System.out.println("孩子节点不能小于1");
return;
}
this.boyCount = n;
for (int i = 1; i <=n; i++) {
//根据n 创建孩子节点
Boy boy = new Boy(i);
if(i == 1){
first = boy;//first指针指向第一个节点
first.next = first;//指向自己
curBoy = first;//当前指针指向第一个节点
}else{
curBoy.next = boy;//指定当前节点的下一节点
boy.next = first;//指向first指针
curBoy = boy;//移动curBoy指针,指向当前节点
}
}
}
//遍历约瑟夫环
public void show(){
if(first == null){
System.out.println("没有小孩节点");
return;
}
//使用第三方变量 temp 遍历
Boy temp = first;
while (true) {
System.out.println("孩子节点是:"+temp.no);
if(first == temp.next){//当前节点的下一节点 == first 说明到尾部了
//遍历完毕
break;
}
temp = temp.next;
}
}
//约瑟夫环 出环序列:
/**
* 游戏规则:
* 1-2-3-4-5的环形对列,
* (1-2-3-4-5)从1 开始数3个数, 3出队,
* (1-2-4-5),从4开始数3个数, 1出队.
* (2-4-5),从2开始数3个数, 5出队,
* (2-4) 从2开始数3个数, 2出队,
* (4) 4出队
*
* beginNum: 表示从第几个小孩开始数数
* countNum: 表示数几个下
*/
public void popBoy(int beginNum,int countNum){
//思路: 1, 定义二个指针, first指针已经指向了第一个节点, helper指针先指向环形链表的最后一个节点
// 2, 开始数数之前, 先将这二个指针,向后移动 beginNum-1次. 即从第3个小孩开始数数, 需要先将指针移动到这里
// 3, 循环数数, 找到要出队的那个节点,怎么找到? 就是将这二个指针, 向后移动 countNum-1次, first指针指的节点就是要出队的节点
// 即 数数countNum-1 后,该节点出队
// 4, 将该节点出队, 并将first指针指向下一节点, helper指针指向first指针
// 5, 循环结束后, 说明只剩一个节点了,该节点出队
if(this.first == null ||beginNum < 1 || beginNum > this.boyCount){
System.out.println("从第几个小孩开始,beginNum不能为0,不能大于环形单向链表的长度: " + this.boyCount);
}
//1, 定义二个指针, first指针已经指向了第一个节点, helper指针先指向环形链表的最后一个节点
Boy helper = first;
while(true){
if (helper.next == first) {
break;//说明到helper指针已经 到链表最后节点
}
helper = helper.next;
}
//2, 开始数数之前, 先将这二个指针,向后移动 beginNum-1次. 即从第3个小孩开始数数, 需要先将指针移动到这里
for (int i = 0; i < beginNum - 1; i++) {
first = first.next;
helper = helper.next;
}
//3, 循环数数, 找到要出队的那个节点,怎么找到? 就是将这二个指针, 向后移动 countNum-1次, first指针指的节点就是要出队的节点
// 即 数数countNum-1 后,该节点出队
while (true) {
if (helper == first) {
break;//此时说明, 只有一个节点了
}
//开始数数,就是将 这二个指针 都向后移动countNum-1 次
for (int i = 0; i < countNum - 1; i++) {
first = first.next;
helper = helper.next;
}
//此时first指针指的就是 要出队的节点
System.out.printf("小孩%d出队\n",first.no);
//4, 将该节点出队, 并将first指针指向下一节点, helper指针指向first指针
first = first.next;
helper.next = first;
}
//5, 循环结束后, 说明只剩一个节点了,该节点出队
System.out.printf("小孩%d出队\n",first.no);
}
}
测试结果:
public static void main(String[] args){
//创建约瑟夫环
SingleCircleLinkList singleCircleLinkList = new SingleCircleLinkList();
singleCircleLinkList.creatYosepfuCircle(5);
singleCircleLinkList.show();
System.out.println("----------");
//约瑟夫 出队
singleCircleLinkList.popBoy(1,3);// 3-1-5-2-4
}

3,java数据结构和算法:约瑟夫环出队顺序, 单向环形链表的应用的更多相关文章
- Java数据结构和算法(一)线性结构之单链表
Java数据结构和算法(一)线性结构之单链表 prev current next -------------- -------------- -------------- | value | next ...
- 《Java数据结构与算法》笔记-CH5-链表-3双端链表
/** * 双端链表的实现 */ class LinkA { public long dData; public LinkA next; public LinkA(long d) { dData = ...
- Java数据结构之单向环形链表(解决Josephu约瑟夫环问题)
1.Josephu(约瑟夫.约瑟夫环)问题: 设编号为1,2,… n的n个人围坐一圈,约定编号为k(1<=k<=n)的人从1开始报数,数到m 的那个人出列,它的下一位又从1开始报数,数到m ...
- 循环列表的Java实现,解决约瑟夫环问题
import java.util.Scanner; /** * 循环列表的Java实现,解决约瑟夫环问题 * * @author LIU * */ public class LinkedList { ...
- 【Java数据结构学习笔记之二】Java数据结构与算法之栈(Stack)实现
本篇是java数据结构与算法的第2篇,从本篇开始我们将来了解栈的设计与实现,以下是本篇的相关知识点: 栈的抽象数据类型 顺序栈的设计与实现 链式栈的设计与实现 栈的应用 栈的抽象数据类型 栈是 ...
- Java数据结构和算法(六)——前缀、中缀、后缀表达式
前面我们介绍了三种数据结构,第一种数组主要用作数据存储,但是后面的两种栈和队列我们说主要作为程序功能实现的辅助工具,其中在介绍栈时我们知道栈可以用来做单词逆序,匹配关键字符等等,那它还有别的什么功能吗 ...
- java数据结构与算法之栈(Stack)设计与实现
本篇是java数据结构与算法的第4篇,从本篇开始我们将来了解栈的设计与实现,以下是本篇的相关知识点: 栈的抽象数据类型 顺序栈的设计与实现 链式栈的设计与实现 栈的应用 栈的抽象数据类型 栈是一种用于 ...
- Java数据结构和算法 - 堆
堆的介绍 Q: 什么是堆? A: 这里的“堆”是指一种特殊的二叉树,不要和Java.C/C++等编程语言里的“堆”混淆,后者指的是程序员用new能得到的计算机内存的可用部分 A: 堆是有如下特点的二叉 ...
- Java数据结构和算法 - 二叉树
前言 数据结构可划分为线性结构.树型结构和图型结构三大类.前面几篇讨论了数组.栈和队列.链表都是线性结构.树型结构中每个结点只允许有一个直接前驱结点,但允许有一个以上直接后驱结点.树型结构有树和二叉树 ...
随机推荐
- 5.PHP与Web页面交互
PHP与Web页面交互 PHP中提供了两种与Web页面交互的方法,一种是通过Web表单提交数据,另一种是通过URL参数传递. 表单提交用户名字和密码: <form name "form ...
- node-util
Node.js 常用工具 util 是一个Node.js 核心模块,提供常用函数的集合,用于弥补核心JavaScript 的功能 过于精简的不足. util.inherits util.inherit ...
- 声明:songzijian这个域名已经被抢注。大家别上了。不是我了。
声明:songzijian这个域名已经被抢注.大家别上了.不是我了.
- 源码分析SpringCloud Gateway如何加载断言(predicates)与过滤器(filters)
我们今天的主角是Gateway网关,一听名字就知道它基本的任务就是去分发路由.根据不同的指定名称去请求各个服务,下面是Gateway官方的解释: https://spring.io/projects/ ...
- (CV学习笔记)梯度下降优化算法
梯度下降法 梯度下降法是训练神经网络最常用的优化算法 梯度下降法(Gradient descent)是一个 ==一阶最优化算法== ,通常也称为最速下降法.要使用梯度下降法找到一个函数的 ==局部最小 ...
- Day003 包机制
包机制 为了更好地组织类,Java提供了包机制,用于区别类名的命名空间. 包语句的语法格式为: package pkg1[.pkg2[.pkg3....]]; 一般利用公司的域名倒置作为包名; 例如: ...
- Yii2访问gii模块403
出现问题 访问Yii2的gii模块没有权限,403 找到原因 在Yii2-gii源码文件中(vendor/yiisoft/yii2-gii/src/Module.php)可以看到有一个配置项$allo ...
- Spring Security 入门篇
本文是一个笔记系列,目标是完成一个基于角色的权限访问控制系统(RBAC),有基本的用户.角色.权限管理,重点在Spring Security的各种配置.万丈高楼平地起,接下来,一步一步,由浅入深,希望 ...
- mysql安装_图文详细安装步骤_让你轻松安装并使用(超详细步骤)
mysql的下载就不用说了,自行到官网下载..(本人下载的是mysql5.0版本) 下面开始正式安装 1.双击mysql_setup.exe后,直接点击Next 2.选择"I accept ...
- 轻量级工具Vite到底牛在哪——一文全知道
转载请注明出处:葡萄城官网,葡萄城为开发者提供专业的开发工具.解决方案和服务,赋能开发者. 原文参考:https://www.sitepoint.com/vitejs-front-end-build- ...