线性表

双向链表

定义

双向链表(双链表),多个结点,每个节点=一个数据域+两个指针域,数据域存数据,指针域分前后,前一个指针域指向前驱结点,后一个指针域指向后继结点。头结点数据域不存储数据,头结点指向前驱结点的指针域的值为null,指向后继结点的指针域指向第一个真正存储数据的结点;尾结点指向后继结点的指针域为null。

图示

代码实现

按照面向对象的思想,设计一个类,描述结点,结点属于链表,所有把结点类作为链表类的内部类来实现

链表类

public class DoublyLinkedList<T> implements Iterable<T>{//头结点private Node head;//尾结点private Node last;//链表长度(元素实际个数,头结点不算)private int N;//--------------------------------------------------//结点类private class Node{//存储数据public T item;//指向上一个结点public Node pre;//指向下一个结点public Node next;//结点类的构造器public Node( Node pre,T item, Node next) {this.pre = pre;this.item = item;this.next = next;}}//--------------------------------------------------//构造器public DoublyLinkedList(){//初始化头结点和尾结点this.head = new Node(null,null,null);this.last = null;//初始化元素个数this.N = 0;}//--------------------------------------------------//清空链表public void clear(){this.head.pre = null;this.head.item = null;this.head.next = null;this.last = null;this.N = 0;}//--------------------------------------------------//返回链表长度public int length(){return N;}
//--------------------------------------------------//判断链表是否为空public boolean isEmpty(){return N == 0;}//--------------------------------------------------//获取第一个元素(不是第一个结点,第一个结点不存数据)public T getFirst(){if(isEmpty()){return null;}return head.next.item;}//--------------------------------------------------//获取最后一个元素public T getLast(){if(isEmpty()){return null;}return last.item;}//--------------------------------------------------//添加元素public void add(T t){if(isEmpty()){//为空//创建新结点,指向前驱结点,也就是头结点Node newNode = new Node(head, t,null);//让新结点成为尾结点last = newNode;//让头结点指向尾结点head.next = last;}else{//链表非空//创建一个oldLast结点代替last,避免冲突Node oldLast = last;//创建新结点,指向了当前尾结点Node newNode = new Node(oldLast, t, null);//让当前尾结点指向新结点last.next = newNode;//让新结点成为尾结点last = newNode;}N++;}//--------------------------------------------------//向指定位置插入元素public void insert(int i, T t){//找到i位置的前一个结点Node preNode = head;for(int index = 0; index<i; index++){preNode = preNode.next;}//找到i位置的结点Node currNode = preNode.next;//创建新结点Node newNode = new Node(preNode,t,currNode);//让原i位置的原前一个结点的指向新结点preNode.next = newNode;//让i位置的结点指向新结点currNode.pre = newNode;//元素个数加1N++;}//--------------------------------------------------//获取指定位置处的元素public T get(int i){Node n = head.next;for(int index = 0; index<i; index++){n = n.next;}return n.item;}//--------------------------------------------------//找到元素t在链表中第一次出现的位置public int indexOf(T t){Node n = head;for(int i = 0; n.next != null; i++){n = n.next;if(n.item.equals(t)){return i;}}return -1;}//--------------------------------------------------//删除指定位置处的元素,并返回该元素public T remove(int i){//找到i位置的前一个结点Node pre = head;for(int index = 0; index<i; index++){pre = pre.next;}//找到i位置的结点Node currNode = pre.next;//找到i位置的下一个结点Node nextNode = currNode.next;//让i位置的前一个节点指向i位置的下一个结点pre.next = nextNode;//让i位置的下一个结点指向i位置的前一个节点nextNode.pre = pre;//元素个数减1N--;return currNode.item;}//--------------------------------------------------@Overridepublic Iterator iterator() {return new DIterator();}//--------------------------------------------------//定义内部类实现iterator接口,重写next和hasNext方法private class DIterator implements Iterator{private Node n;public DIterator(){this.n = head;}@Overridepublic boolean hasNext() {return n.next != null;}@Overridepublic Object next() {n = n.next;return n.item;}}
}

测试类

public class DoublyLinkedListTest {public static void main(String[] args) {DoublyLinkedList dll = new DoublyLinkedList();dll.add("姚明");dll.add("科比");dll.add("乔丹");//测试迭代遍历System.out.println("----------------测试遍历--------------------");for(String obj : dll){System.out.println(obj);}System.out.println("----------------测试插入--------------------");dll.insert(1,"杜兰特");dll.insert(2,"奥尼尔");for(String obj : dll){System.out.println(obj);}System.out.println("---------获取第一个和最后一个结点的值------------");System.out.println(dll.getFirst());;System.out.println(dll.getLast());System.out.println("---------获取指定元素第一次出现的位置-------------");System.out.println(dll.indexOf("科比"));System.out.println("--------------测试删除----------------------");System.out.println(dll.remove(2));System.out.println("--------------清空链表----------------------");dll.clear();for(String obj : dll){System.out.println(obj);}}
}

结果

----------------测试遍历--------------------
姚明
科比
乔丹
----------------测试插入--------------------
姚明
杜兰特
奥尼尔
科比
乔丹
---------获取第一个和最后一个结点的值------------
姚明
乔丹
---------获取指定元素第一次出现的位置-------------
3
--------------测试删除----------------------
奥尼尔
--------------清空链表----------------------

数据结构与算法(java):线性表(链表-双向链表)相关推荐

  1. 黑马程序员 C语言数据结构与算法之线性表(链表/栈/队列/顺序表)

    C语言 链表基础知识清晰讲解(黑马) 讲的蛮好,就是音质不太好,有时听不清讲的啥! [黑马]数据结构与算法之线性表(链表/栈/队列/顺序表)[配套源码 嘛蛋,看错了,这是java的... 文章目录 链 ...

  2. 从零开始学数据结构和算法(二)线性表的链式存储结构

    链表 链式存储结构 定义 线性表的链式存储结构的特点是用一组任意的存储单元的存储线性表的数据元素,这组存储单元是可以连续的,也可以是不连续的. 种类 结构图 单链表 应用:MessageQueue 插 ...

  3. rsa算法c语言实现_数据结构与算法之线性表-顺序表实现(C语言版本)

    原文托管在Github: https://github.com/shellhub/blog/issues/52 数据结构与算法之线性表-顺序表实现(C语言版本) 前言 数据结构与算法是一个程序员必备的 ...

  4. 数据结构与算法(一) 线性表之顺序表

     线性表是一种最简单.最常用的数据结构,根据存储方式可以分为顺序表和链表.  顺序表: 顺序表指的是用一组地址连续的存储单元依次存储线性表的数据元素,称为线性表的顺序存储结构或顺序映像(sequent ...

  5. 数据结构与算法之线性结构链表

    数据结构与算法之线性结构链表 这一篇文章主要介绍的是通过java实现单链表.循环链表和双向循环链表,仅供自己复习使用,如有什么不足之处,欢迎指出. 单链表: package xianxingjiego ...

  6. 数据结构和算法基础--线性表

    数据结构和算法基础–线性表 数据结构 = 数据的逻辑结构+数据的存储结构+数据的运算 [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-28ek7MfI-164242629 ...

  7. Java数据结构与算法_线性表_顺序表与链表

    文章目录 线性表 顺序表 顺序表API设计 顺序表的代码实现 链表 单向链表 双向链表 总结 线性表 概述 线性表是最基本.最简单.也是最常用的一种数据结构. 一个线性表是n个具有相同特性的数据元素的 ...

  8. 数据结构与算法之线性表(超详细顺序表、链表)

    原创公众号:bigsai 文章已收录在 全网都在关注的数据结构与算法学习仓库 欢迎star 前言 通过前面数据结构与算法基础知识我么知道了数据结构的一些概念和重要性,那么我们今天总结下线性表相关的内容 ...

  9. Java数据结构和算法:线性表

    线性表的定义 线性表(linear-list)是最常用最简单的一种数据结构.一个线性表是n (n≥0)个相同类型数据元素的有限序列.记为: L= (a1, a2 , - , an ). 其中,L是表名 ...

  10. 数据结构(算法)-线性表2(单链表)

    为什么80%的码农都做不了架构师?>>>    /** 单链表 双链表1,空的线性表setNull(L) 2,insert 加入元素 3,根据位置查找元素 4,查找所有元素 5,删除 ...

最新文章

  1. Java泛型之mybatis,基于spring MVC 和 MyBatis 泛型的代码生成模板
  2. r语言和metawin_如何创建R的HelloWorld包(Windows或Linux环境下)
  3. APUE学习之多线程编程(二):线程同步
  4. Boost::context模块fiber的circle测试程序
  5. JAVA程序运行原理分析
  6. MyBatisPlus_AR篇_入门试炼_06
  7. CCNP学习之路之QOS配置命令
  8. 自己动手写打印机监控程序
  9. 基因组所三代单分子测序PacBio完成技术升级—超长读长助力基因组学研究
  10. 小哦php远程文件下载,PHP:远程文件大小,无需下载文件
  11. Java剑开天门(二)
  12. Centos 7.4 防火墙关闭命令
  13. 10分钟读懂什么是产品定位
  14. InstallShield 2010集成.net Framework 4的安装包制作
  15. SemEval-2022 Task 6 有意讽刺检测
  16. 常用坐标系及SuperMap投影转换
  17. python练习 006 圆的周长与面积
  18. 路漫漫其修远兮,吾将上下而求“锁”​
  19. Java中增强for循环 for(int x:number) continue中的label: 标签 continue标签
  20. 计算机教师教育教学特长,计算机教师教学计划

热门文章

  1. aruba交换机配置命令_aruba配置手册
  2. JQuery Ajax 参数含有特殊字符
  3. Windows上搭建PHP开发环境
  4. 论文笔记 Acquiring Common Sense Spatial Knowledge through Implicit Spatial Templates (AAAI2018)
  5. 《大数据时代》读后感(一)
  6. c语言实现三角形面积公式字母,c语言计算三角形面积代码
  7. 基于spring boot的实验自动评分系统
  8. 解决No version of NDK matched the requested version编译报错的问题
  9. flv是什么视频格式?怎么把flv转换成mp4?
  10. 2014年3月CCF软考试题