管理单向链表的缺点分析:

单向链表,查找的方向只能是一个方向,而双向链表可以向前或者向后查找。

单向链表不能自我删除,需要靠辅助节点 ,而双向链表,则可以自我删除,所以前面我们单链表删除时节点,总是找到temp,temp是待删除节点的前一个节点。

示意图

对上图的说明:

分析双向链表的遍历、添加、修改、删除的操作思路:

1)遍历:方法和单链表一样,只是可以向前查找,也可以向后查找

2)添加:(默认添加到双向链表的最后)

  • 先找到双向链表的最后的节点
  • temp.next = newHeroNode;
  • newHeroNode.pre = temp;

3)修改:思路和原来的单向链表一样

4)删除

  • 因为是双向链表,因此可以实现某个节点的自我删除
  • 直接找到要删除的这个节点,如temp
  • temp.pre.next = temp.next;
  • temp.next.pre = temp.pre;

代码实现:

链表节点结构类

// 定义HeroNode2 , 每个HeroNode 对象就是一个节点
class HeroNode2 {
public int no;
public String name;
public String nickname;
public HeroNode2 next; // 指向下一个节点, 默认为null
public HeroNode2 pre; // 指向前一个节点, 默认为null
// 构造器 public HeroNode2(int no, String name, String nickname) {
this.no = no;
this.name = name;
this.nickname = nickname;
} // 为了显示方法,我们重新toString
@Override
public String toString() {
return "HeroNode [no=" + no + ", name=" + name + ", nickname=" + nickname + "]";
} }

链表操作类:

// 创建一个双向链表的类
class DoubleLinkedList { // 先初始化一个头节点, 头节点不要动, 不存放具体的数据
private HeroNode2 head = new HeroNode2(0, "", ""); // 返回头节点
public HeroNode2 getHead() {
return head;
} // 遍历双向链表的方法
// 显示链表[遍历]
public void list() {
// 判断链表是否为空
if (head.next == null) {
System.out.println("链表为空");
return;
}
// 因为头节点,不能动,因此我们需要一个辅助变量来遍历
HeroNode2 temp = head.next;
while (true) {
// 判断是否到链表最后
if (temp == null) {
break;
}
// 输出节点的信息
System.out.println(temp);
// 将temp后移, 一定小心
temp = temp.next;
}
} // 添加一个节点到双向链表的最后.
public void add(HeroNode2 heroNode) { // 因为head节点不能动,因此我们需要一个辅助遍历 temp
HeroNode2 temp = head;
// 遍历链表,找到最后
while (true) {
// 找到链表的最后
if (temp.next == null) {//
break;
}
// 如果没有找到最后, 将将temp后移
temp = temp.next;
}
// 当退出while循环时,temp就指向了链表的最后
// 形成一个双向链表
temp.next = heroNode;
heroNode.pre = temp;
} // 修改一个节点的内容, 可以看到双向链表的节点内容修改和单向链表一样
// 只是 节点类型改成 HeroNode2
public void update(HeroNode2 newHeroNode) {
// 判断是否空
if (head.next == null) {
System.out.println("链表为空~");
return;
}
// 找到需要修改的节点, 根据no编号
// 定义一个辅助变量
HeroNode2 temp = head.next;
boolean flag = false; // 表示是否找到该节点
while (true) {
if (temp == null) {
break; // 已经遍历完链表
}
if (temp.no == newHeroNode.no) {
// 找到
flag = true;
break;
}
temp = temp.next;
}
// 根据flag 判断是否找到要修改的节点
if (flag) {
temp.name = newHeroNode.name;
temp.nickname = newHeroNode.nickname;
} else { // 没有找到
System.out.printf("没有找到 编号 %d 的节点,不能修改\n", newHeroNode.no);
}
} // 从双向链表中删除一个节点,
// 说明
// 1 对于双向链表,我们可以直接找到要删除的这个节点
// 2 找到后,自我删除即可
public void del(int no) { // 判断当前链表是否为空
if (head.next == null) {// 空链表
System.out.println("链表为空,无法删除");
return;
} HeroNode2 temp = head.next; // 辅助变量(指针)
boolean flag = false; // 标志是否找到待删除节点的
while (true) {
if (temp == null) { // 已经到链表的最后
break;
}
if (temp.no == no) {
// 找到的待删除节点的前一个节点temp
flag = true;
break;
}
temp = temp.next; // temp后移,遍历
}
// 判断flag
if (flag) { // 找到
// 可以删除
// temp.next = temp.next.next;[单向链表]
temp.pre.next = temp.next;
// 这里我们的代码有问题?
// 如果是最后一个节点,就不需要执行下面这句话,否则出现空指针
if (temp.next != null) {
temp.next.pre = temp.pre;
}
} else {
System.out.printf("要删除的 %d 节点不存在\n", no);
}
}
}

Java数据结构之双向链表的更多相关文章

  1. JAVA数据结构--LinkedList双向链表

    链表是一种物理存储单元上非连续.非顺序的存储结构,数据元素的逻辑顺序是通过链表中的指针链接次序实现的.链表由一系列结点(链表中每一个元素称为结点)组成,结点可以在运行时动态生成.每个结点包括两个部分: ...

  2. java数据结构-05双向链表

    一.双向链式存储: ①简述:要是节点中包含两个指针部分,一个指向前驱元,一个指向后继元,Java中LinkedList集合类的实现就是双向链表 (以下图片为网络收集,侵删) ②特点:数据是非连续的,链 ...

  3. Java 数据结构之双向链表

    一.概述: 1.什么是双向链表: 链表中的每个节点即指向前面一个节点,也指向后面一个节点,就像丢手绢游戏一样,每个人都手拉手 2.从头部插入 要对链表进行判断,如果为空则设置尾节点为新添加的节点,如果 ...

  4. 图解Java数据结构之双向链表

    上一篇文章说到了单链表,也通过案例具体实现了一下,但是单链表的缺点也显而易见. 单向链表查找的方向只能是一个方向 单向链表不能自我删除,需要靠辅助节点 而双向链表则能够很轻松地实现上面的功能. 何为双 ...

  5. Java数据结构之线性表

    从这里开始将要进行Java数据结构的相关讲解,Are you ready?Let's go~~ java中的数据结构模型可以分为一下几部分: 1.线性结构 2.树形结构 3.图形或者网状结构 接下来的 ...

  6. (6)Java数据结构-- 转:JAVA常用数据结构及原理分析

    JAVA常用数据结构及原理分析  http://www.2cto.com/kf/201506/412305.html 前不久面试官让我说一下怎么理解java数据结构框架,之前也看过部分源码,balab ...

  7. Java数据结构和算法(一)线性结构

    Java数据结构和算法(一)线性结构 数据结构与算法目录(https://www.cnblogs.com/binarylei/p/10115867.html) 线性表 是一种逻辑结构,相同数据类型的 ...

  8. 一文掌握关于Java数据结构所有知识点(欢迎一起完善)

    在我们学习Java的时候,很多人会面临我不知道继续学什么或者面试会问什么的尴尬情况(我本人之前就很迷茫).所以,我决定通过这个开源平台来帮助一些有需要的人,通过下面的内容,你会掌握系统的Java学习以 ...

  9. Java数据结构和算法(四)--链表

    日常开发中,数组和集合使用的很多,而数组的无序插入和删除效率都是偏低的,这点在学习ArrayList源码的时候就知道了,因为需要把要 插入索引后面的所以元素全部后移一位. 而本文会详细讲解链表,可以解 ...

随机推荐

  1. HDU-2444-The Accomodation of Students(二分图判定,最大匹配)

    链接: https://vjudge.net/problem/HDU-2444#author=634579757 题意: There are a group of students. Some of ...

  2. kafka消费者示范代码(Java)

    1.将kafka里lib目录下(除jar包外还有别的东西)所有的jar包导入工程中. 2.代码 public static void main(String[] args) { //声明连接属性 Pr ...

  3. 【ipc-mq】根据mq的key查看使用进程

    使用ipcs -q可以得到key与msqid的对应关系,从而找到msgid webadmin@172.172.179.3:/usr/local/webapps/test_ma[17:17:36]$ i ...

  4. msyql 优化之五不要

    1.尽量不要有空判断的语句,因为空判断将导致全表扫描,而不是索引扫描. 对于空判断这种情况,可以考虑对这个列创建数据库默认值 //空判断将导致全表扫描 select small_id from sma ...

  5. PHP+FLASH大文件断点续传功能分享

    1.使用PHP的创始人 Rasmus Lerdorf 写的APC扩展模块来实现(http://pecl.php.net/package/apc) APC实现方法: 安装APC,参照官方文档安装,可以使 ...

  6. Devexpress MVC Gridview 获取到增删改的所有行数据(JSON) 并使用SQL事物保存数据

    //ModalChargeGridView Gridview的名字//Con_Shp_Chg 数据库表名//ConShpChgUID UID或者是标识列//gs_Language 语言(中英文)//l ...

  7. Nginx的正则表达式

    Nginx (engine x) 是一个高性能的HTTP和反向代理服务,也是一个IMAP/POP3/SMTP服务.Nginx是由伊戈尔·赛索耶夫为俄罗斯访问量第二的Rambler.ru站点(俄文:Ра ...

  8. sar性能监控

    1.安装sar: yum -y install sysstat 第一次使用sar命令会提示如下错误:“无法打开 /var/log/sa/sa13: 没有那个文件或目录”. 这里的值13是当天的日期,如 ...

  9. 第十周java学习总结

    目录 第十周java学习总结 学习内容 代码上传截图 代码链接 第十周java学习总结 学习内容 第12章 Java多线程机制 主要内容 Java中的线程 Thread类与线程的创建 线程的常用方法 ...

  10. hibernate缓存机制与N+1问题

    在项目中遇到的趣事 本文基于hibernate缓存机制与N+1问题展开思考, 先介绍何为N+1问题 再hibernate中用list()获得对象: /** * 此时会发出一条sql,将30个学生全部查 ...