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

无头单向非循环java版的模拟实现

【本节目标】

1.ArrayList的缺陷

2.链表

1. ArrayList的缺陷

上节课已经熟悉了 ArrayList 的使用,并且进行了简单模拟实现。通过源码知道, ArrayList 底层使用数组来存储元素:
public class ArrayList<E> extends AbstractList<E>implements List<E>, RandomAccess, Cloneable, java.io.Serializable
{// ...
// 默认容量是10private static final int DEFAULT_CAPACITY = 10;//...
// 数组:用来存储元素transient Object[] elementData; // non-private to simplify nested class access// 有效元素个数private int size;public ArrayList(int initialCapacity) {if (initialCapacity > 0) {this.elementData = new Object[initialCapacity];} else if (initialCapacity == 0) {this.elementData = EMPTY_ELEMENTDATA;} else {throw new IllegalArgumentException("Illegal Capacity: "+initialCapacity);}}
// ...
}
由于其底层是一段连续空间,当 ArrayList 任意位置插入或者删除元素时,就需要将后序元素整体往前或者往后 搬移,时间复杂度为 O(n) ,效率比较低,因此 ArrayList 不适合做任意位置插入和删除比较多的场景 。因此: java集合中又引入了LinkedList ,即链表结构。

2. 链表

2.1 链表的概念及结构

链表是一种 物理存储结构上非连续 存储结构,数据元素的 逻辑顺序 是通过链表中的 引用链接 次序实现的 。
实际中链表的结构非常多样,以下情况组合起来就有 8 种链表结构:
1. 单向或者双向
2. 带头或者不带头
3. 循环或者非循环
虽然有这么多的链表的结构,但是我们重点掌握两种 :
头单向非循环链表结构简单,一般不会单独用来存数据。实际中更多是作为其他数据结构的子结构,如哈希桶、图的邻接表等等。另外这种结构在笔试面试中出现很多。
无头双向链表:在Java的集合框架库中LinkedList底层实现就是无头双向循环链表。

2.2 无头单向非循环链表的实现

接口:
public interface Ilinklist {// 1、无头单向非循环链表实现//头插法void addFirst(int val);//尾插法void addLast(int val);//任意位置插入,第一个数据节点为0号下标void addIndex(int index,int val);//查找是否包含关键字key是否在单链表当中boolean contains(int key);//删除第一次出现关键字为key的节点void remove(int key);//删除所有值为key的节点void removeAllKey(int key);//得到单链表的长度int size();//清空单链表void clear();//展示单链表void display();}

要有链表首先得有节点
如下就是使用内部类创建了个头结点
有数值和next节点的地址
在创建一个成员变量head,指向头结点。未初始化默认为null
我们可以写链表的插入
链表的头插不需要考虑是否为空的情况
链表的尾差需要考虑为空的情况,如果是空就直接返回,不进行插入
while(cur.next!=null)
这个循环是遍历到最后一个链表,再将它的next改为新节点的地址即可
随机位置插入
1.考虑给的位置是否合法
2.给的是0或者给的链表长度
3.在范围内的值找到index前一个的链表
4.进行连接
1.合法性
写了一个异常类
写了一个函数捕捉这个异常
再用try-catch来处理异常
2.给的是0或者给的链表长度
如果给的是0就进行头插
如果给的是链表长度就进行尾差
剩下的就比较简单
用了一个函数进行寻找index的前一个位置
再进行连接
链表的打印
再测试下插入是否满足要求
可见插入是满足需求的
是否包含某个元素

删除第一个数值为val的节点
测试
删除所有为为val的节点
测试
确实没有1出现,可见全部删除
删除所有存在val值的节点还有一个方法,创建一个哨兵位
测试
也是可以的

2.3总代码

接口

public interface Ilinklist {// 1、无头单向非循环链表实现//头插法void addFirst(int val);//尾插法void addLast(int val);//任意位置插入,第一个数据节点为0号下标void addIndex(int index,int val);//查找是否包含关键字key是否在单链表当中boolean contains(int val);//删除第一次出现关键字为key的节点void remove(int val);//删除所有值为key的节点void removeAllKey(int val);//得到单链表的长度int getSize();void clear();void display();}

indexNotLegalException.java

public class indexNotLegalException extends   RuntimeException{public indexNotLegalException(){}public indexNotLegalException(String msg){super(msg);}
}

LinkList.java

public class LinkList implements Ilinklist {static class ListNode{public int val;ListNode next;public ListNode(int val) {this.val = val;}}ListNode head;@Overridepublic void addFirst(int val) {//链表的头插ListNode node=new ListNode(val);node.next=head;head=node;}public void addLast(int val){//链表的尾差ListNode node=new ListNode(val);if(head==null){head=node;return;}ListNode cur=head;while(cur.next!=null){cur=cur.next;}cur.next=node;}public int getSize(){//获取链表的长度ListNode cur=head;int count=0;while(cur!=null){count++;cur=cur.next;}return count;}public  void addIndex(int index,int val){//1.判断合法性try{cheakIndexofAddIndex(index);}catch(indexNotLegalException e){e.printStackTrace();return;}//2.index==0||index==size()if(index==0){addFirst(val);return;}if(index==getSize()){addLast(val);return;}//3.找到index的前一个位置ListNode cur=findIndexSubOne(index);//4.进行连接ListNode node=new ListNode(val);node.next=cur.next;cur.next=node;}@Overridepublic boolean contains(int val) {ListNode cur=head;while(cur!=null){if(cur.val==val){return true;}cur=cur.next;}return false;}@Overridepublic void remove(int val) {   //删除第一个节点为val的值if(head==null){return;}ListNode cur=head;if(cur.val==val){head=head.next;return;}while(cur.next!=null){if(cur.next.val==val){cur.next=cur.next.next;return;}cur=cur.next;}}@Overridepublic void removeAllKey(int val) {//删除链表所有值为val的节点/*      if(head==null){return;}ListNode prev=head;ListNode cur=head.next;while(cur!=null){if(cur.val==val){prev.next=cur.next;cur=cur.next;}else{prev=cur;cur=cur.next;}}if(head.val==val){head=head.next;}*/ListNode Head=new ListNode(0);Head.next=head;ListNode temp=Head;while(temp.next!=null){if(temp.next.val==val){temp.next=temp.next.next;}else{temp=temp.next;}}head=Head.next;}@Overridepublic void clear() {}@Overridepublic void display() {ListNode cur=head;while(cur!=null){System.out.print(cur.val+" ");cur=cur.next;}System.out.println();}private void cheakIndexofAddIndex(int index) throws indexNotLegalException{//判断指定位置插入的index是否合法if(index<0||index>getSize()){throw new indexNotLegalException("AddIndex的index不合法");}}private ListNode findIndexSubOne(int index){ListNode cur=head;while(index-1>0){cur=cur.next;index--;}return cur;}}

test.java

public class test {public static void main(String[] args) {LinkList linkList=new LinkList();linkList.addFirst(1);linkList.addFirst(1);linkList.addFirst(1);linkList.addFirst(1);//上面是链表的头插linkList.display();System.out.println("==============");linkList.removeAllKey(1);//删除所有拥有1的节点linkList.display();}
}

相关文章:

无头单向非循环java版的模拟实现

【本节目标】 1.ArrayList的缺陷 2.链表 1. ArrayList的缺陷 上节课已经熟悉了 ArrayList 的使用&#xff0c;并且进行了简单模拟实现。通过源码知道&#xff0c; ArrayList 底层使用数组来存储元素&#xff1a; public class ArrayList<E> extends AbstractList<…...

Bert Score-文本相似性评估

Bert Score Bert Score 是基于BERT模型的一种方法。它通过计算两个句子在BERT模型中的嵌入编码之间的余弦相似度来评估它们的相似度。BERTScore考虑了上下文信息和语义信息&#xff0c;因此能够更准确地衡量句子之间的相似度。 安装 pip install bert-score 使用例子 一个…...

Pyenv管理Python版本,conda之外的另一套python版本管理解决方案

简介 Pyenv 是一个 python 解释器管理工具&#xff0c;可以对计算机中的多个 python 版本进行管理和切换。为什么要用 pyenv 管理python呢&#xff0c;用过的 python 人都知道&#xff0c;python 虽然是易用而强大的编程语言&#xff0c;但是 python 解释器却有多个版本&#…...

快速实现AI搜索!Fivetran 支持 Milvus 作为数据迁移目标

Fivetran 现已支持 Milvus 向量数据库作为数据迁移的目标&#xff0c;能够有效简化 RAG 应用和 AI 搜索中数据源接入的流程。 数据是 AI 应用的支柱&#xff0c;无缝连接数据是充分释放数据潜力的关键。非结构化数据对于企业搜索和检索增强生成&#xff08;RAG&#xff09;聊天…...

css的页面布局属性

CSS Flexbox&#xff08;Flexible Box Layout&#xff09;是一种用于页面布局的CSS3规范&#xff0c;它提供了一种更加高效的方式来布置、对齐和分配容器内元素的空间&#xff0c;即使它们的大小是未知或者动态变化的。Flexbox很容易处理一维布局&#xff0c;即在一个方向上&am…...

RTE 大会报名丨AI 时代新基建:云边端架构和 AI Infra ,RTE2024 技术专场第二弹!

所有 AI Infra 都在探寻规格和性能的最佳平衡&#xff0c;如何构建高可用的云边端协同架构&#xff1f; 语音 AI 实现 human-like 的最后一步是什么&#xff1f; AI 视频的爆炸增长&#xff0c;给新一代编解码技术提出了什么新挑战&#xff1f; 当大模型进化到实时多模态&am…...

【React】入门Day01 —— 从基础概念到实战应用

目录 一、React 概述 二、开发环境创建 三、JSX 基础 四、React 的事件绑定 五、React 组件基础使用 六、组件状态管理 - useState 七、组件的基础样式处理 快速入门 – React 中文文档 一、React 概述 React 是什么 由 Meta 公司开发&#xff0c;是用于构建 Web 和原生…...

<<机器学习实战>>10-11节笔记:生成器与线性回归手动实现

10生成器与python实现 如果是曲线规律的数据集&#xff0c;则需要把模型变复杂。如果是噪音较大&#xff0c;则需要做特征工程。 随机种子的知识点补充&#xff1a; 根据不同库中的随机过程&#xff0c;需要用对应的随机种子&#xff1a; 比如 llist(range(5)) random.shuf…...

链表OJ经典题目及思路总结(一)

目录 前言1.移除元素1.1 链表1.2 数组 2.双指针2.1 找链表的中间结点2.2 找倒数第k个结点 总结 前言 解代码题 先整体&#xff1a;首先数据结构链表的题一定要多画图&#xff0c;捋清问题的解决思路&#xff1b; 后局部&#xff1a;接着考虑每一步具体如何实现&#xff0c;框架…...

初识chatgpt

GPT到底是什么 首先&#xff0c;我们需要了解GPT的全称&#xff1a;Generative Pre-trained Transformer&#xff0c;即三个关键词&#xff1a;生成式 预训练 变换模型。 &#xff08;1&#xff09;什么是生成式&#xff1f; 即能够生成新的文本序列。 &#xff08;2&#…...

【60天备战2024年11月软考高级系统架构设计师——第33天:云计算与大数据架构——大数据处理框架的应用场景】

随着大数据技术的发展&#xff0c;越来越多的企业开始采用大数据处理框架来解决实际问题。理解这些框架的应用场景对于架构师来说至关重要。 大数据处理框架的应用场景 实时数据分析&#xff1a;使用Apache Kafka与Apache Spark结合&#xff0c;可以实现对实时数据流的处理与…...

如何设计具体项目的数据库管理

### 例三&#xff1a;足协的数据库管理算法 #### 角色&#xff1a; - **ESFP学生**&#xff1a;小明 - **ENTP老师**&#xff1a;张老师 #### 主题&#xff1a;足协的数据库管理算法 --- **张老师**&#xff1a;小明&#xff0c;今天我们来讨论一下足协的数据库管理算法。你…...

对于 Vue CLI 项目如何引入Echarts以及动态获取数据

&#x1f680;个人主页&#xff1a;一颗小谷粒 &#x1f680;所属专栏&#xff1a;Web前端开发 很荣幸您能阅读我的文章&#xff0c;诚请评论指点&#xff0c;欢迎欢迎 ~ 目录 1、数据画卷—Echarts介绍 1.1 什么是Echarts&#xff1f; 1.2 Echarts官网地址 2、Vue CLI 项目…...

【Linux笔记】在VMware中,为基于NAT模式运行的CentOS虚拟机设置固定的网络IP地址

一、配置VMware虚拟网络 1、打开VMware虚拟网络编辑器&#xff1a; 点击VMware主界面上方的“编辑”菜单&#xff0c;选择“虚拟网络编辑器”。 2、选择NAT模式网络&#xff1a; 在虚拟网络编辑器中&#xff0c;选择VMnet8&#xff08;或其他NAT模式的网络&#xff09;。 取消勾…...

一文上手Kafka【中】

一、发送消息细节 在发送消息的特别注意: 在版本 3.0 中&#xff0c;以前返回 ListenableFuture 的方法已更改为返回 CompletableFuture。为了便于迁移&#xff0c;2.9 版本添加了一个方法 usingCompletableFuture&#xff08;&#xff09;&#xff0c;该方法为 CompletableFu…...

Ubuntu如何如何安装tcpdump

在Ubuntu上安装tcpdump非常简单&#xff0c;可以通过以下步骤完成&#xff1a; 打开终端。 更新包列表&#xff1a; 首先&#xff0c;更新你的包管理器的包列表&#xff1a; sudo apt update 安装tcpdump&#xff1a; 使用以下命令安装tcpdump&#xff1a; sudo apt install …...

3-3 AUTOSAR RTE 对SR Port的作用

返回总目录->返回总目录<- 一、前言 RTE作为SWC和BSW之间的通信机构,支持Sender-Receiver方式实现ECU内及ECU间的通信。 对于Sender-Receiver Port支持三种模式: 显式访问:若运行实体采用显示模式的S/R通信方式,数据读写是即时的;隐式访问:当多个运行实体需要读取…...

hive/impala/mysql几种数据库的sql常用写法和函数说明

做大数据开发的时候&#xff0c;会在几种库中来回跳&#xff0c;同一个需求&#xff0c;不同库函数和写法会有出入&#xff0c;在此做汇总沉淀。 1. hive 1. 日期差 DATEDIFF(CURRENT_DATE(),wdjv.creation_date) < 30 30天内的数据 2.impala 3. spark 4. mysql 1.时间差…...

论文阅读:LM-Cocktail: Resilient Tuning of Language Models via Model Merging

论文链接 代码链接 Abstract 预训练的语言模型不断进行微调,以更好地支持下游应用。然而,此操作可能会导致目标领域之外的通用任务的性能显著下降。为了克服这个问题,我们提出了LM Cocktail,它使微调后的模型在总体上保持弹性。我们的方法以模型合并(Model Merging)的形…...

8640 希尔(shell)排序

### 思路 希尔排序是一种基于插入排序的排序算法&#xff0c;通过将待排序数组分割成多个子序列分别进行插入排序来提高效率。初始增量d为n/2&#xff0c;之后每次减半&#xff0c;直到d为1。 ### 伪代码 1. 读取输入的待排序关键字个数n。 2. 读取n个待排序关键字并存储在数组…...

国防科技大学计算机基础课程笔记02信息编码

1.机内码和国标码 国标码就是我们非常熟悉的这个GB2312,但是因为都是16进制&#xff0c;因此这个了16进制的数据既可以翻译成为这个机器码&#xff0c;也可以翻译成为这个国标码&#xff0c;所以这个时候很容易会出现这个歧义的情况&#xff1b; 因此&#xff0c;我们的这个国…...

代理篇12|深入理解 Vite中的Proxy接口代理配置

在前端开发中,常常会遇到 跨域请求接口 的情况。为了解决这个问题,Vite 和 Webpack 都提供了 proxy 代理功能,用于将本地开发请求转发到后端服务器。 什么是代理(proxy)? 代理是在开发过程中,前端项目通过开发服务器,将指定的请求“转发”到真实的后端服务器,从而绕…...

Java求职者面试指南:Spring、Spring Boot、MyBatis框架与计算机基础问题解析

Java求职者面试指南&#xff1a;Spring、Spring Boot、MyBatis框架与计算机基础问题解析 一、第一轮提问&#xff08;基础概念问题&#xff09; 1. 请解释Spring框架的核心容器是什么&#xff1f;它在Spring中起到什么作用&#xff1f; Spring框架的核心容器是IoC容器&#…...

《C++ 模板》

目录 函数模板 类模板 非类型模板参数 模板特化 函数模板特化 类模板的特化 模板&#xff0c;就像一个模具&#xff0c;里面可以将不同类型的材料做成一个形状&#xff0c;其分为函数模板和类模板。 函数模板 函数模板可以简化函数重载的代码。格式&#xff1a;templa…...

Docker 本地安装 mysql 数据库

Docker: Accelerated Container Application Development 下载对应操作系统版本的 docker &#xff1b;并安装。 基础操作不再赘述。 打开 macOS 终端&#xff0c;开始 docker 安装mysql之旅 第一步 docker search mysql 》〉docker search mysql NAME DE…...

关于uniapp展示PDF的解决方案

在 UniApp 的 H5 环境中使用 pdf-vue3 组件可以实现完整的 PDF 预览功能。以下是详细实现步骤和注意事项&#xff1a; 一、安装依赖 安装 pdf-vue3 和 PDF.js 核心库&#xff1a; npm install pdf-vue3 pdfjs-dist二、基本使用示例 <template><view class"con…...

深入理解Optional:处理空指针异常

1. 使用Optional处理可能为空的集合 在Java开发中&#xff0c;集合判空是一个常见但容易出错的场景。传统方式虽然可行&#xff0c;但存在一些潜在问题&#xff1a; // 传统判空方式 if (!CollectionUtils.isEmpty(userInfoList)) {for (UserInfo userInfo : userInfoList) {…...

协议转换利器,profinet转ethercat网关的两大派系,各有千秋

随着工业以太网的发展&#xff0c;其高效、便捷、协议开放、易于冗余等诸多优点&#xff0c;被越来越多的工业现场所采用。西门子SIMATIC S7-1200/1500系列PLC集成有Profinet接口&#xff0c;具有实时性、开放性&#xff0c;使用TCP/IP和IT标准&#xff0c;符合基于工业以太网的…...

API网关Kong的鉴权与限流:高并发场景下的核心实践

&#x1f525;「炎码工坊」技术弹药已装填&#xff01; 点击关注 → 解锁工业级干货【工具实测|项目避坑|源码燃烧指南】 引言 在微服务架构中&#xff0c;API网关承担着流量调度、安全防护和协议转换的核心职责。作为云原生时代的代表性网关&#xff0c;Kong凭借其插件化架构…...

C++实现分布式网络通信框架RPC(2)——rpc发布端

有了上篇文章的项目的基本知识的了解&#xff0c;现在我们就开始构建项目。 目录 一、构建工程目录 二、本地服务发布成RPC服务 2.1理解RPC发布 2.2实现 三、Mprpc框架的基础类设计 3.1框架的初始化类 MprpcApplication 代码实现 3.2读取配置文件类 MprpcConfig 代码实现…...