【java-数据结构14-双向链表的增删查改2】

   上一篇文章中,我们已经对双向链表进行一些基本操作,本篇文章我们继续通过对链表的增删查改来加深对链表的理解~同时有任何不懂的地方可以在评论区留言讨论,也可以私信小编~觉得小编写的还可以的可以留个关注支持一下~话不多说正片开始~

注意:上篇文章少了一些图,这里做些补充重新发一遍

1.任意位置插入

1.对插入位置进行合法性判断

2.如果等于0即为头插法,等于size即为尾插法

小于0大于saize都是不可以的,代码如下

private void checkIndex(int index) {if(index < 0 || index > size()) {throw new IndexOutOfException("index 不合法!"+index);}}

上面我们抛出一个自定义异常 ,也不要忘记定义一个异常类,代码如下

 public class IndexOutOfException extends RuntimeException{public IndexOutOfException() {}public IndexOutOfException(String message) {super(message);}}

3.定义cur,也就是要插入的位置

代码如下

public void addIndex(int index,int data){checkIndex(index);if(index == 0) {addFirst(data);return;}if(index == size()) {addLast(data);return;}ListNode cur = searchIndex(index);ListNode node = new ListNode(data);node.next = cur;cur.prev.next = node;node.prev = cur.prev;cur.prev = node;}

调用测试

public class test {public static void main(String[] args) {MyLinkedList myLinkedList = new MyLinkedList();myLinkedList.addFirst(56);myLinkedList.addFirst(45);myLinkedList.addFirst(34);myLinkedList.addFirst(23);myLinkedList.addFirst(12);myLinkedList.addLast(67);myLinkedList.display();myLinkedList.addIndex(0,999);myLinkedList.display();}

运行截图 

2.删除第一次出现的key节点

  如果是单链表,我们是需要找到要删除的前一个节点的,让删除的节点被跳过即可

  双链表则不需要那么麻烦,我们先看中间节点,直接找到要删除的节点cur,让cur.prev.next = cur.next; cur.next.prev = cur.prev;即可 如图

接下来我们讨论如果要删除的是头节点 :先让head = head.next并且head.prev = null

注意:那么如果只有一节点呢head = head.nex代码执行完毕后head就为null,那么head.prev = null就会异常,那么我们要加一个前置条件if:head!=null,如果head等于null,手动把last置为空即可

下面我们讨论要删除的是尾巴节点cur.prev.next = cur.next; last = last.prev

代码如下

 public void remove(int key){ListNode cur = head;while (cur != null) {if(cur.val == key) {//删除头节点if(cur == head) {head = head.next;if(head != null) {//考虑只有一个节点的情况下head.prev = null;}else {last = null;}}else {//删除中间节点 和  尾巴节点if(cur.next != null) {//删除中间节点cur.prev.next = cur.next;cur.next.prev = cur.prev;}else {//尾巴节点cur.prev.next = cur.next;last = last.prev;}}return;}else {cur = cur.next;}}}

调用测试

 public static void main(String[] args) {MyLinkedList myLinkedList = new MyLinkedList();myLinkedList.addFirst(56);myLinkedList.addFirst(45);myLinkedList.addFirst(34);myLinkedList.addFirst(23);myLinkedList.addFirst(12);myLinkedList.addLast(67);myLinkedList.display();myLinkedList.remove(23);myLinkedList.display();}

运行截图

 

3.删除所有出现的key节点

    此题逻辑与上题基本相同,只是我们上一个题删除第一个节点后就返回了,我们只要让cur继续往后走即可

代码如下

public void removeAllKey(int key){ListNode cur = head;while (cur != null) {if(cur.val == key) {//删除头节点if(cur == head) {head = head.next;if(head != null) {//考虑只有一个节点的情况下head.prev = null;}else {last = null;}}else {//删除中间节点 和  尾巴节点if(cur.next != null) {//删除中间节点cur.prev.next = cur.next;cur.next.prev = cur.prev;}else {//尾巴节点cur.prev.next = cur.next;last = last.prev;}}cur = cur.next;//return;}else {cur = cur.next;}}}

调用测试

 public static void main(String[] args) {MyLinkedList myLinkedList = new MyLinkedList();myLinkedList.addFirst(56);myLinkedList.addFirst(45);myLinkedList.addFirst(12);myLinkedList.addFirst(12);myLinkedList.addFirst(12);myLinkedList.addLast(67);myLinkedList.display();myLinkedList.removeAllKey(12);myLinkedList.display();}

运行截图 

4.清空链表

head,last置为null,或者一个一个置null,如图

 

但此时还有head,last两个节点,手动置空即可 

代码如下

 public void clear(){ListNode cur = head;while (cur != null) {ListNode curNext = cur.next;cur.prev = null;cur.next = null;cur = curNext;}head = null;last = null;}

调用测试

 public static void main(String[] args) {MyLinkedList myLinkedList = new MyLinkedList();myLinkedList.addFirst(56);myLinkedList.addFirst(45);myLinkedList.addFirst(12);myLinkedList.addFirst(12);myLinkedList.addFirst(12);myLinkedList.addLast(67);myLinkedList.display();myLinkedList.clear();myLinkedList.display();}

运行截图

5.库中的linkedlist方法使用

 到此为止,我们手动创建链表并对链表进行增删查改就结束的,其实我们还可以通过 库当中的linkedlist,直接使用,下面我们做具体演示

1.导入类:import java.util.List

2.创建链表。

  List<Integer> list1 = new LinkedList<>();

下面是一些方法,这里不做演示了

 

6.LinkedList遍历 

1.for循环

这个方法前面有讲过,这里不多赘述

2.for,each循环

代码如下

 public static void main(String[] args) {List<Integer> list = new LinkedList<>();list.add(1);list.add(1);list.add(3);for (Integer X:list) {System.out.println(X);}}

运行截图

 

3.迭代器· 

使用迭代器要导入类:import java.util.ListIterator;

代码如下

 public static void main(String[] args) {List<Integer> list = new LinkedList<>();list.add(1);list.add(1);list.add(3);ListIterator<Integer> it = list.listIterator();while(it.hasNext()){System.out.print(it.next()+ " ");}}

4.迭代器反向遍历

 

public static void main(String[] args) {List<Integer> list = new LinkedList<>();list.add(1);list.add(1);list.add(3);ListIterator<Integer> rit = list.listIterator(list.size());while (rit.hasPrevious()){System.out.print(rit.previous() +" ");}System.out.println();}

 

到此为止,我们链表的章节就可以跟大家说在再见了,下一篇文章,我们将会进入栈和队列的学习,觉得小编讲的还可以的可以留个关注~我们下期再见~ 谢谢观看~

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/697921.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【精读Yamamoto】方向性连接如何丰富神经网络的功能复杂度 | 体外神经元培养实验 | 脉冲神经元模型(SNN) | 状态转移模型

探索大脑的微观世界&#xff1a;方向性连接如何丰富神经网络的功能复杂度 在神经科学领域&#xff0c;理解大脑如何通过其复杂的网络结构实现高级功能一直是一个核心议题。最近&#xff0c;一项由Nobuaki Monma和Hideaki Yamamoto博士领导的研究为我们提供了新的视角&#xff…

Docker 入门篇(八)-- Docker Compose 使用指南

一、Docker Compose 简介 Docker Compose 是用于定义和运行多容器 Docker 应用程序的工具。通过 Compose&#xff0c;您可以使用 YML 文件来配置应用程序需要的所有服务。然后&#xff0c;使用一个命令&#xff0c;就可以从 YML 文件配置中创建并启动所有服务。 Compose 使用…

记录接口请求偶发504 Gateway Time-out问题

项目场景&#xff1a; 我们将服务部署到A公司服务器中&#xff0c;使用了共五台服务器&#xff0c;分别是&#xff1a;1.NG服务器 2.日志服务器 3.缓存服务器 4.应用服务器1 5.应用服务器2 。而请求过来首先到达的是他们的物理代理服务器&#xff0c;然后再转发请求到我们的ng…

利用一段代码轻松绕过PHP授权系统

第一步&#xff1a;首先你需要改名全局文件 比如说全局文件 common.php&#xff0c;那么 你将他改为core.php 第二步&#xff1a;创建文件 创建一个文件&#xff0c;和改名前的全局文件名称一样&#xff0c;然后把以下代码复制进去就OK了 代码如下&#xff1a; <?php…

OFDM802.11a的FPGA实现(十四)data域的设计优化,挤掉axi协议传输中的气泡

原文链接&#xff08;相关文章合集&#xff09;&#xff1a;OFDM 802.11a的xilinx FPGA实现 目录 1.前言 2.data域的时序要求 3.Debug 1.前言 前面12篇文章详细讲述了&#xff0c;OFDM 802.11a发射部分data域的FPGA实现和验证&#xff0c;今天对data域的设计做一个总结。在…

【vue2项目经验总结:a标签干扰路由】

当我们点击页面中的a标签实现跳转时&#xff0c;会发现网页上方的路由也切换成了a标签的id值&#xff1a; 刷新后页面也会变成空白&#xff1a; 解决方法&#xff1a; 添加Click方法&#xff0c;传入的参数与id值保持一致 scrollIntoView() 方法&#xff0c;将该元素滚动到…

快解析Tplink端口映射如何设置

Tplink作为国内知名路由器品牌&#xff0c;有着广泛的用户群体。使用快解析端口映射是实现内网服务器被外网访问必须要做的设置&#xff0c;很多对网络不懂得小白不知道该到哪里去做&#xff0c;下面我就讲解一下tplink路由器如何做端口映射。 1&#xff1a;访问路由器 &#…

Peter算法小课堂—序列切割

讲序列切割之前&#xff0c;先来个铺垫 高手集训 题目描述&#xff1a; 课程表里有连续的n天可以供你选择&#xff0c;每天都有专题课程。其中第i天的专题趣味程度为h[i]。假设你选择了其中连续的若干天&#xff0c;从第l天到第r天。那么&#xff0c; 训练效果 h[l]*1 h[…

【实践】使用vscode来debug go程序的尝鲜

配置 首先&#xff0c;当然得配置好vscode 的go环境&#xff0c; 装个go插件就基本满足了 配置 launch.json, 可以配置多个环境的程序启动参数&#xff08;很友好&#xff09; {"version": "0.2.0","configurations": [{"name": &…

嵌入式CAN通信协议详解分析

CAN协议简介 CAN是控制器局域网络(Controller Area Network)的简称,它是由研发和生产汽车电子产品著称的德国BOSCH公司开发的,并最终成为国际标准(ISO11519),是国际上应用最广泛的现场总线之一。 CAN总线协议已经成为汽车计算机控制系统和嵌入式工业控制局域网的标准总线…

JavaSE——集合框架一(2/7)-Collection集合的遍历方式-迭代器、增强for循环、Lambda、案例

目录 Collection的遍历方式 迭代器 增强for循环&#xff08;foreach&#xff09; Lambda表达式遍历集合 案例 需求与分析 代码部分 运行结果 Collection的遍历方式 迭代器 选代器是用来遍历集合的专用方式&#xff08;数组没有选代器&#xff09;&#xff0c;在Java中…

初始Django

初始Django 一、Django的历史 ​ Django 是从真实世界的应用中成长起来的&#xff0c;它是由堪萨斯&#xff08;Kansas&#xff09;州 Lawrence 城中的一个网络开发小组编写的。它诞生于 2003 年秋天&#xff0c;那时 Lawrence Journal-World 报纸的程序员 Adrian Holovaty 和…