当前位置: 首页 > news >正文

Java链表及源码解析

文章目录

  • 创建一个ILindkedList接口创建方法(模拟实现链表方法)
  • 创建MyLinkedList来实现接口的方法
  • 创建链表节点
    • addFirst方法(新增头部属性)
    • addLast方法(新增到末尾一个属性)
    • remove方法(删除指定属性)
    • addIndex方法(任意位置添加一个元素属性)
    • removeAll(删除所有指定元素)
    • display打印
    • contains(链表中包含某个元素)
    • size(获取链表元素的数量)
  • clean(清空)
  • MyLinkedList代码如下:
  • Test代码:

  1. **链表是通过逻辑储存的方式通过节点的引用来获取元素值,每个节点包含两个部分 首先第一部分是value元素值。 第二部分是next来获取下个节点的地址,通过next来串联各个地址获取其中的value元素
    有序数组如果想要新增或者删减元素需要从头开始遍历逐个进行覆盖确保有序数组中的有序,时间复杂度为O(m*n)。
    链表的复杂度相对有序数组要方便他的时间复杂度分别是O(1)和O(N)。 **
    在这里插入图片描述

创建一个ILindkedList接口创建方法(模拟实现链表方法)

public interface ILinkedList {//首位置新增元素public void addFirst(int data);//最后位置新增元素public void addLast(int data);//在指定位置新增元素public void addIndex(int index,int data);//在链表中删除key元素public void remove(int key);//删除所有key的元素public void removeAll(int key);//打印链表元素public void display();//是否包含datapublic boolean contains(int data);//获取链表中元素的大小public  int size();void clean();
}

创建MyLinkedList来实现接口的方法

import javax.xml.soap.Node;public class MyLinkedList implements ILinkedList{//创建一个static内部类来初始化节点属性static class NodeList{//元素值public int value;//节点指向的下一个地址public NodeList next;//构造方法只给value通过这个值来next下一个节点public NodeList(int value) {this.value = value;}}

创建链表节点

 //这里可以尝试创建一个链表public void createLinkedList(){NodeList node1=new NodeList(23);NodeList node2=new NodeList(25);NodeList node3=new NodeList(38);NodeList node4=new NodeList(55);//通过获取的对象来访问next链接下一个节点实现链接node1.next=node2;node2.next=node3;node3.next=node4;//这里node4的next节点为空值//head作为头部来访问各个节点this.head=node1;}

addFirst方法(新增头部属性)

在这里插入图片描述

 @Overridepublic void addFirst(int data) {//增加一个元素到链表中,增加到头部//将data元素放入到类中NodeList node=new NodeList(data);NodeList cur=this.head;//这里node.next来获取头部地址node.next=head;//将node赋给headhead=node;}

addLast方法(新增到末尾一个属性)

在这里插入图片描述

 @Overridepublic void addLast(int data) {//增加一个元素到末尾NodeList node=new NodeList(data);NodeList cur=this.head;//这里我们查找最后一个位置的next节点是否为null,如果是null;while(cur.next!=null){cur = cur.next;}//循环出来cur.next的节点为nullcur.next=node;}

remove方法(删除指定属性)

在这里插入图片描述

    @Overridepublic void remove(int key) {//删除指定元素的next地址节点if(this.head==null){return;}//得到前缀NodeList cur = findRemoveKey(key);//判断返回值是否是空的if(cur==null){System.out.println("未找到该元素"+key);return;}//将cur.next给到dele得到节点NodeList dele=cur.next;//将后一个节点的next给到cur.next从而指向其他节点dele原有节点消失cur.next=dele.next;}private NodeList findRemoveKey(int key){NodeList cur=this.head;//cur.next不等于null数值while(cur.next!=null){if(cur.next.value==key){return cur;}//cur.next节点获取下一个curcur = cur.next;}return null;}

addIndex方法(任意位置添加一个元素属性)

在这里插入图片描述

removeAll(删除所有指定元素)

在这里插入图片描述

   @Overridepublic void removeAll(int key) {if(this.head==null){return;}NodeList pre=this.head;NodeList cur=pre.next;//cur!=null说明有数据while(cur!=null){//value值为key进入循环if(cur.value==key){//pre的下个节点为cur的下一个节点,取消掉cur=key这个节点的链接pre.next=cur.next;cur=cur.next;}else{//如果不等于pre要跳到cur的位置来继续作为前一项pre=cur;//cur获取下一项cur=cur.next;}}//不要忽略头部,如果是key要替换掉if(this.head.value==key){this.head=this.head.next;}}
    @Overridepublic void addIndex(int index, int data)throws ErrorRuntimeExcepetion {//给一个位置,放入data元素//如果index的值小于0或者大于本身长度抛出异常显示下标try {if(index<0||index>size()){throw new ErrorRuntimeExcepetion("范围不准确"+index);}}catch (ErrorRuntimeExcepetion e){e.printStackTrace();return;}//如果index的位置是0或者index的位置是最后一个if(index==0){addFirst(data);}if(index==size()){addLast(data);}//走到这里index的值为其范围内容,首先获取index-1的位置NodeList cur = searchPre(index);//生成data元素链表NodeList node=new NodeList(data);if(cur==null){return;}//将原来cur.index的地址赋值给node.index来后移node.next=cur.next;//将现在的cur.index的地址指向nodecur.next=node;}private NodeList searchPre(int index){NodeList cur=this.head;//求一个index-1的范围int count=0;while(count<index-1){cur=cur.next;count++;}//获取到index-1位置的curreturn cur;}

display打印

 @Overridepublic void display() {//创建一个对象接收head值,来进行打印NodeList cur=this.head;//cur不等于nullwhile(cur!=null){//通过cur引用value来打印元素System.out.print(cur.value+" ");//通过next中下一个节点的地址来访问元素cur=cur.next;}System.out.println();}

contains(链表中包含某个元素)

   @Overridepublic boolean contains(int data) {//链表中是否包含dataNodeList cur=this.head;if(cur.value==data){//如果value是data返回truereturn true;}else{while(cur.next!=null){//循环每个节点判断是否为dataif(cur.next.value==data){return true;}cur=cur.next;}}return false;}

size(获取链表元素的数量)

@Overridepublic int size() {//获取链表的元素大小NodeList cur = this.head;//如果cur中为null没有任何元素大小是0if (cur == null) {return 0;}int count=0;//计数while(cur!=null){count++;cur=cur.next;}return count;}

clean(清空)

在这里插入图片描述

   @Overridepublic void clean() {if(this.head==null){return;}//将每个节点置为空属性并且回收NodeList cur=this.head;while(cur!=null){NodeList curNext=cur.next;cur.next=null;cur=curNext;}//置空nullthis.head=null;}

MyLinkedList代码如下:

import javax.xml.soap.Node;public class MyLinkedList implements ILinkedList{//创建一个static内部类来初始化节点属性static class NodeList{//元素值public int value;//节点指向的下一个地址public NodeList next;//构造方法只给value通过这个值来next下一个节点public NodeList(int value) {this.value = value;}}//创建一个带头链表来获取当前的节点第一个元素public NodeList head;//这里可以尝试创建一个链表public void createLinkedList(){NodeList node1=new NodeList(23);NodeList node2=new NodeList(25);NodeList node3=new NodeList(38);NodeList node4=new NodeList(55);//通过获取的对象来访问next链接下一个节点实现链接node1.next=node2;node2.next=node3;node3.next=node4;//这里node4的next节点为空值//head作为头部来访问各个节点this.head=node1;}@Overridepublic void addFirst(int data) {//增加一个元素到链表中,增加到头部//将data元素放入到类中NodeList node=new NodeList(data);NodeList cur=this.head;//这里node.next来获取头部地址node.next=head;//将node赋给headhead=node;}@Overridepublic void addLast(int data) {//增加一个元素到末尾NodeList node=new NodeList(data);NodeList cur=this.head;//这里我们查找最后一个位置的next节点是否为null,如果是null;while(cur.next!=null){cur = cur.next;}//循环出来cur.next的节点为nullcur.next=node;}@Overridepublic void remove(int key) {//删除指定元素的next地址节点if(this.head==null){return;}//得到前缀NodeList cur = findRemoveKey(key);//判断返回值是否是空的if(cur==null){System.out.println("未找到该元素"+key);return;}//将cur.next给到dele得到节点NodeList dele=cur.next;//将后一个节点的next给到cur.next从而指向其他节点dele原有节点消失cur.next=dele.next;}private NodeList findRemoveKey(int key){NodeList cur=this.head;//cur.next不等于null数值while(cur.next!=null){if(cur.next.value==key){return cur;}//cur.next节点获取下一个curcur = cur.next;}return null;}@Overridepublic void removeAll(int key) {if(this.head==null){return;}NodeList pre=this.head;NodeList cur=pre.next;//cur!=null说明有数据while(cur!=null){//value值为key进入循环if(cur.value==key){//pre的下个节点为cur的下一个节点,取消掉cur=key这个节点的链接pre.next=cur.next;cur=cur.next;}else{//如果不等于pre要跳到cur的位置来继续作为前一项pre=cur;//cur获取下一项cur=cur.next;}}//不要忽略头部,如果是key要替换掉if(this.head.value==key){this.head=this.head.next;}}@Overridepublic void addIndex(int index, int data)throws ErrorRuntimeExcepetion {//给一个位置,放入data元素//如果index的值小于0或者大于本身长度抛出异常显示下标try {if(index<0||index>size()){throw new ErrorRuntimeExcepetion("范围不准确"+index);}}catch (ErrorRuntimeExcepetion e){e.printStackTrace();return;}//如果index的位置是0或者index的位置是最后一个if(index==0){addFirst(data);}if(index==size()){addLast(data);}//走到这里index的值为其范围内容,首先获取index-1的位置NodeList cur = searchPre(index);//生成data元素链表NodeList node=new NodeList(data);if(cur==null){return;}//将原来cur.index的地址赋值给node.index来后移node.next=cur.next;//将现在的cur.index的地址指向nodecur.next=node;}private NodeList searchPre(int index){NodeList cur=this.head;//求一个index-1的范围int count=0;while(count<index-1){cur=cur.next;count++;}//获取到index-1位置的curreturn cur;}@Overridepublic void display() {//创建一个对象接收head值,来进行打印NodeList cur=this.head;//cur不等于nullwhile(cur!=null){//通过cur引用value来打印元素System.out.print(cur.value+" ");//通过next中下一个节点的地址来访问元素cur=cur.next;}System.out.println();}@Overridepublic boolean contains(int data) {//链表中是否包含dataNodeList cur=this.head;if(cur.value==data){//如果value是data返回truereturn true;}else{while(cur.next!=null){//循环每个节点判断是否为dataif(cur.next.value==data){return true;}cur=cur.next;}}return false;}@Overridepublic int size() {//获取链表的元素大小NodeList cur = this.head;//如果cur中为null没有任何元素大小是0if (cur == null) {return 0;}int count=0;//计数while(cur!=null){count++;cur=cur.next;}return count;}@Overridepublic void clean() {if(this.head==null){return;}//将每个节点置为空属性并且回收NodeList cur=this.head;while(cur!=null){NodeList curNext=cur.next;cur.next=null;cur=curNext;}//置空nullthis.head=null;}
}

Test代码:

public class Test {public static void main(String[] args) {MyLinkedList myLinkedList=new MyLinkedList();//这里创建链表对象
//    myLinkedList.createLinkedList();//访问创建的链表myLinkedList.addFirst(10);myLinkedList.addFirst(10);myLinkedList.addLast(10);myLinkedList.addLast(10);myLinkedList.addIndex(3,39);myLinkedList.addIndex(5,10);System.out.println(myLinkedList.contains(39));myLinkedList.display();myLinkedList.remove(39);myLinkedList.removeAll(10);myLinkedList.display();myLinkedList.clean();myLinkedList.addFirst(1);myLinkedList.display();System.out.println("链表中的元素大小为"+myLinkedList.size());}
}

#运行结果
在这里插入图片描述

相关文章:

Java链表及源码解析

文章目录 创建一个ILindkedList接口创建方法(模拟实现链表方法)创建MyLinkedList来实现接口的方法创建链表节点addFirst方法&#xff08;新增头部属性&#xff09;addLast方法&#xff08;新增到末尾一个属性&#xff09;remove方法&#xff08;删除指定属性&#xff09;addInd…...

十、快速入门go语言之方法

文章目录 方法:one: 方法的概念:star2: 内嵌类型的方法和继承:star2: 多重继承 &#x1f4c5; 2024年5月9日 &#x1f4e6; 使用版本为1.21.5 方法 1️⃣ 方法的概念 ⭐️ 在Go语言中没有类这个概念&#xff0c;可以使用结构体来实现&#xff0c;那类方法呢&#xff1f;Go也…...

JVM 处理多线程并发执行

JVM&#xff08;Java Virtual Machine&#xff09;在处理多线程并发执行方面具有强大的支持&#xff0c;主要依赖于其内置的线程模型、内存模型以及同步机制。 JVM 通过以下关键机制和组件来管理多线程并发执行&#xff1a; 1. 线程模型 Java 线程与操作系统线程&#xff1a;…...

【D3.js in Action 3 精译_039】4.3 D3 面积图的绘制方法及其边界标签的添加

当前内容所在位置&#xff1a; 第四章 直线、曲线与弧线的绘制 ✔️ 4.1 坐标轴的创建&#xff08;上篇&#xff09; 4.1.1 D3 中的边距约定&#xff08;中篇&#xff09;4.1.2 坐标轴的生成&#xff08;中篇&#xff09; 4.1.2.1 比例尺的声明&#xff08;中篇&#xff09;4.1…...

布谷直播源码部署服务器关于数据库配置的详细说明

布谷直播源码搭建部署配置接口数据库 /public/db.php&#xff08;2019年8月后的系统在该路径下配置数据库&#xff0c;老版本继续走下面的操作&#xff09; 在项目代码中执行命令安装依赖库&#xff08;⚠️注意&#xff1a;如果已经有了vendor内的依赖文件的就不用执行了&am…...

Xfce桌面设置右键菜单:用右键打开VSCode

前言 AlmaLinux安装VSCode之后始终没有找到如何用右键菜单打开VSCode&#xff0c;比Windows麻烦多了。每次都需要先找到文件夹&#xff0c;然后用系统自带的Open In Terminal打开终端&#xff0c;再输入code .&#xff0c;才能够在当前文件夹中快速打开VSCode。那么&#xff0…...

【NLP自然语言处理】深入探索Self-Attention:自注意力机制详解

目录 &#x1f354; Self-attention的特点 &#x1f354; Self-attention中的归一化概述 &#x1f354; softmax的梯度变化 3.1 softmax函数的输入分布是如何影响输出的 3.2 softmax函数在反向传播的过程中是如何梯度求导的 3.3 softmax函数出现梯度消失现象的原因 &…...

Pytorch训练时报nan

0. 引言 Pytorch训练时在batchN时loss为nan。经过断点检查发现在batchN-1时&#xff0c;网络参数非nan&#xff0c;输出非nan&#xff0c;但梯度为nan&#xff0c;导致网络参数已经全部被更新为nan&#xff0c;遇到这种情况应该如何排查&#xff0c;如何避免&#xff1f;由于导…...

JavaScript定时器详解:setTimeout与setInterval的使用与注意事项

在JavaScript中&#xff0c;定时器用于在指定的时间间隔后或周期性地执行代码。JavaScript 提供了两种主要的定时器函数&#xff1a;setTimeout 和 setInterval。以下是它们的详细解释和实现方式&#xff1a; 1. setTimeout setTimeout 函数用于在指定的毫秒数后执行一次函数…...

CSS——选择器、PxCook软件、盒子模型

选择器 结构伪类选择器 作用&#xff1a;根据元素的结构关系查找元素。 <!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, initial-scale1.0&quo…...

Mysql 大表limit查询优化原理实战

文章目录 1 大表查询无条件优化&原理(入门)2 大表查询带 条件 优化&原理(进阶)2.1 where 后面的查询字段只有一个时&#xff0c;要求该字段是索引字段2.2 where 后面的查询字段有多个时&#xff0c;尽量让查询字段为索引字段且字段值基数大 3 大表查询带 排序 优化&…...

在vscode中开发运行uni-app项目

确保电脑已经安装配置好了node、vue等相关环境依赖 进行项目的创建 vue create -p dcloudio/uni-preset-vue 项目名 vue create -p dcloudio/uni-preset-vue uni-app 选择模版 这里选择【默认模版】 项目创建成功后在vscode中打开 第一次打开项目 pages.json 文件会报错&a…...

【JavaEE初阶 — 多线程】Thread的常见构造方法&属性

目录 Thread类的属性 1.Thread 的常见构造方法 2.Thread 的几个常见属性 2.1 前台线程与后台线程 2.2 setDaemon() 2.3 isAlive() Thread类的属性 Thread 类是JVM 用来管理线程的一个类&#xff0c;换句话说&#xff0c;每个线程都有一个唯一的Thread 对象与之关联&am…...

ctfshow(316)--XSS漏洞--反射性XSS

Web316 进入界面&#xff1a; 审计 显示是关于反射性XSS的题目。 思路 首先想到利用XSS平台解题&#xff0c;看其他师傅的wp提示flag是在cookie中。 当前页面的cookie是flagyou%20are%20not%20admin%20no%20flag。 但是这里我使用XSS平台&#xff0c;显示的cookie还是这样…...

ubuntu22.04安装conda

在 Ubuntu 22.04 上安装 Conda 可以通过以下步骤进行&#xff1a; 下载 Miniconda&#xff08;轻量级版本的 Conda&#xff09;&#xff1a; 打开终端并运行以下命令以下载 Miniconda 安装脚本&#xff1a; wget https://repo.anaconda.com/miniconda/Miniconda3-latest-Linux-…...

D58【python 接口自动化学习】- python基础之异常

day58 异常捕获 学习日期&#xff1a;20241104 学习目标&#xff1a;异常 -- 74 自定义异常捕获&#xff1a;如何定义业务异常&#xff1f; 学习笔记&#xff1a; 自定义异常的用途 自定义异常的方法 # 抛出一个异常 # raise ValueError(value is error) # ValueError: val…...

Java项目实战II基于Spring Boot的便利店信息管理系统(开发文档+数据库+源码)

目录 一、前言 二、技术介绍 三、系统实现 四、文档参考 五、核心代码 六、源码获取 全栈码农以及毕业设计实战开发&#xff0c;CSDN平台Java领域新星创作者&#xff0c;专注于大学生项目实战开发、讲解和毕业答疑辅导。获取源码联系方式请查看文末 一、前言 在快节奏的…...

Java-日期计算工具类DateCalculator

DateCalculator是用于日期计算的工具类。这个工具类将包括日期的加减、比较、周期计算、日期 范围生成等功能。 import java.time.LocalDate; import java.time.LocalDateTime; import java.time.LocalTime; import java.time.Period; import java.time.temporal.ChronoUnit;…...

单片机串口接收状态机STM32

单片机串口接收状态机stm32 前言 项目的芯片stm32转国产&#xff0c;国产芯片的串口DMA接收功能测试不通过&#xff0c;所以要由原本很容易配置的串口空闲中断触发DMA接收数据的方式转为串口逐字节接收的状态机接收数据 两种方式各有优劣&#xff0c;不过我的芯片已经主频跑…...

ipv6的 fc00(FC00::/7) 和 fec0(FEC0::/10)

ipv6的 fc00(FC00::/7)&#xff08;唯一本地地址&#xff09; 替代了 fec0(FEC0::/10) &#xff08;站点本地地址&#xff0c;已弃用&#xff09; ipv6的 fc00(FC00::/7) 替代了 fec0(FEC0::/10) , 在IPv6地址中&#xff0c;FC00::/7&#xff08;通常简写为FC00&#xff09;和…...

观成科技:隐蔽隧道工具Ligolo-ng加密流量分析

1.工具介绍 Ligolo-ng是一款由go编写的高效隧道工具&#xff0c;该工具基于TUN接口实现其功能&#xff0c;利用反向TCP/TLS连接建立一条隐蔽的通信信道&#xff0c;支持使用Let’s Encrypt自动生成证书。Ligolo-ng的通信隐蔽性体现在其支持多种连接方式&#xff0c;适应复杂网…...

应用升级/灾备测试时使用guarantee 闪回点迅速回退

1.场景 应用要升级,当升级失败时,数据库回退到升级前. 要测试系统,测试完成后,数据库要回退到测试前。 相对于RMAN恢复需要很长时间&#xff0c; 数据库闪回只需要几分钟。 2.技术实现 数据库设置 2个db_recovery参数 创建guarantee闪回点&#xff0c;不需要开启数据库闪回。…...

Spark 之 入门讲解详细版(1)

1、简介 1.1 Spark简介 Spark是加州大学伯克利分校AMP实验室&#xff08;Algorithms, Machines, and People Lab&#xff09;开发通用内存并行计算框架。Spark在2013年6月进入Apache成为孵化项目&#xff0c;8个月后成为Apache顶级项目&#xff0c;速度之快足见过人之处&…...

3403. 从盒子中找出字典序最大的字符串 I

3403. 从盒子中找出字典序最大的字符串 I 题目链接&#xff1a;3403. 从盒子中找出字典序最大的字符串 I 代码如下&#xff1a; class Solution { public:string answerString(string word, int numFriends) {if (numFriends 1) {return word;}string res;for (int i 0;i &…...

Java多线程实现之Thread类深度解析

Java多线程实现之Thread类深度解析 一、多线程基础概念1.1 什么是线程1.2 多线程的优势1.3 Java多线程模型 二、Thread类的基本结构与构造函数2.1 Thread类的继承关系2.2 构造函数 三、创建和启动线程3.1 继承Thread类创建线程3.2 实现Runnable接口创建线程 四、Thread类的核心…...

Linux C语言网络编程详细入门教程:如何一步步实现TCP服务端与客户端通信

文章目录 Linux C语言网络编程详细入门教程&#xff1a;如何一步步实现TCP服务端与客户端通信前言一、网络通信基础概念二、服务端与客户端的完整流程图解三、每一步的详细讲解和代码示例1. 创建Socket&#xff08;服务端和客户端都要&#xff09;2. 绑定本地地址和端口&#x…...

CSS设置元素的宽度根据其内容自动调整

width: fit-content 是 CSS 中的一个属性值&#xff0c;用于设置元素的宽度根据其内容自动调整&#xff0c;确保宽度刚好容纳内容而不会超出。 效果对比 默认情况&#xff08;width: auto&#xff09;&#xff1a; 块级元素&#xff08;如 <div>&#xff09;会占满父容器…...

【从零学习JVM|第三篇】类的生命周期(高频面试题)

前言&#xff1a; 在Java编程中&#xff0c;类的生命周期是指类从被加载到内存中开始&#xff0c;到被卸载出内存为止的整个过程。了解类的生命周期对于理解Java程序的运行机制以及性能优化非常重要。本文会深入探寻类的生命周期&#xff0c;让读者对此有深刻印象。 目录 ​…...

android13 app的触摸问题定位分析流程

一、知识点 一般来说,触摸问题都是app层面出问题,我们可以在ViewRootImpl.java添加log的方式定位;如果是touchableRegion的计算问题,就会相对比较麻烦了,需要通过adb shell dumpsys input > input.log指令,且通过打印堆栈的方式,逐步定位问题,并找到修改方案。 问题…...

Java后端检查空条件查询

通过抛出运行异常&#xff1a;throw new RuntimeException("请输入查询条件&#xff01;");BranchWarehouseServiceImpl.java // 查询试剂交易&#xff08;入库/出库&#xff09;记录Overridepublic List<BranchWarehouseTransactions> queryForReagent(Branch…...