Data structure (java version)

linked list (linkedList)

It is a common basic data structure and a linear table, but it does not store data in a linear order, but stores the address of the next node in each node.

Linked list can be divided into singly linked list and doubly linked list.

A singly linked list contains two values: the value of the current node and a link to the next node. 

A doubly linked list has three integer values: value, backward node link, forward node link.

Java LinkedList (linked list) is similar to ArrayList and is a commonly used data container.

Compared with ArrayList, LinkedList's addition and deletion operations are more efficient, while search and modification operations are less efficient.

Use ArrayList when:

  • A certain element in the list is frequently accessed.
  • It is only necessary to add and remove elements at the end of the list.

Use LinkedList when:

  • You need to iterate through a loop to access certain elements of the list.
  • It is necessary to frequently add and delete elements at the beginning, middle, and end of the list.

LinkedList inherits the AbstractSequentialList class.

LinkedList implements the Queue interface and can be used as a queue.

LinkedList implements the List interface, and can perform related operations on the list.

LinkedList implements the Deque interface and can be used as a queue.

LinkedList implements the Cloneable interface, enabling cloning.

LinkedList implements the java.io.Serializable interface, which supports serialization and can be transmitted through serialization.

The LinkedList class is located in the java.util package

But here I followed Lao Han to realize the addition, deletion and modification of the single linked list

package com.czy.linkedlist;

/**
 * 1.
 * 2.
 * 3.单链表的创建
 **/
public class SingleLinkedListDemo {
    public static void main(String[] args) {

        /*
        * 进行测试
        * 先创建节点
        * */

        HeroNode people1 = new HeroNode(1, "tom", "boss");
        HeroNode people2 = new HeroNode(2, "jack", "worker");
        HeroNode people3 = new HeroNode(3, "luo", "worker2");
        HeroNode people4 = new HeroNode(4, "adt", "worker3");
        HeroNode people5 = new HeroNode(5, "klo", "worker4");

        //创建要给链表
        SingleLinkedList singleLinkedList = new SingleLinkedList();
        //加入add
        /*singleLinkedList.add(people1);
        singleLinkedList.add(people2);
        singleLinkedList.add(people3);
        singleLinkedList.add(people4);
        singleLinkedList.add(people5);
*/

        //加入addByOrder
        singleLinkedList.addByOrder(people1);
        singleLinkedList.addByOrder(people4);
        singleLinkedList.addByOrder(people5);
        singleLinkedList.addByOrder(people3);
        singleLinkedList.addByOrder(people2);
        //打印出来
        singleLinkedList.list();

        //测试修改节点的代码
        HeroNode wsw = new HeroNode(2, "WSW", "007");
        singleLinkedList.update(wsw);

        System.out.println("修改后的链表:");
        singleLinkedList.list();


        //测试删除节点的代码
        singleLinkedList.del(1);
        singleLinkedList.del(4);
        System.out.println("删除后的链表:");
        singleLinkedList.list();


    }
}

class SingleLinkedList{
    //先初始化一个头结点,头结点不要动,不存放具体的数据
    private HeroNode head = new HeroNode(0,"","");

    //添加节点到单向链表
    //思路,当不考虑编号顺序时
    //1.找到链表的最后节点
    //2.将最后这个节点的next域 指向 新的节点
    public void add(HeroNode heroNode){
        //因为头结点不能动,因此我们需要一个辅助遍历指针 temp
        HeroNode temp = head;
        //遍历链表,找到最后
        while (true) {
            //找到链表的最后
            if (temp.next == null){
                break;
            }
            //如果没有找到最后,将temp后移
            temp = temp.next;
        }
        //当退出while循环时,temp就指向了链表的最后
        //将最后这个节点的next,指向新的节点
        temp.next = heroNode;
    }

    //第二种方式在添加英雄时,根据排名将英雄插入到指定位置
    //(如果有排名,则添加失败,并给出提示)
    public void addByOrder(HeroNode heroNode){
        //因为头结点不能动,因此我们仍然通过一个辅助指针(变量)来帮助找到添加的位置
        //因为单链表,我们找的temp 是位于 添加位置前一个节点,否则插入不了
        HeroNode temp = head;
        boolean flag = false;  // flag标志添加的编号是否存在,默认为false
        while (true){
            if (temp.next == null){ //说明temp已在链表的最后
                break;
            }
            if (temp.next.no > heroNode.no){  //位置找到,就在temp的后面插入
                break;
            }else if (temp.next.no == heroNode.no){//说明希望添加的heroNode的编号依然存在
                flag = true;//说明编号存在
                break;
            }
            temp = temp.next;
        }
        //判断flag的值
        if (flag){//不能添加,说明编号已经存在
            System.out.printf("准备插入的编号已经存在,不能加入\n",heroNode.no);
        }else {
            //插入到链表中,temp的后面
            heroNode.next = temp.next;
            temp.next = heroNode;
        }
    }

    //修改节点的信息,根据no编号来修改,即no编号不能修改
    //说明
    //1.根据newHeroNode 的 no 来修改即可
    public void update(HeroNode newHeroNode){
        //判断是否为空
        if (head.next == null){
            System.out.println("链表为空~~~~");
            return;
        }
        //找到需要修改的节点,根据no来编写
        //定义一个辅助变量
        HeroNode 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.head节点不能动 因此我们仍然通过一个辅助指针(变量)来帮助找到待删除节点的前一个节点
    //2.说明我们在比较时,是temp.next.no 和 需要删除的节点的no比较
    public void del(int no){
        HeroNode temp = head;
        boolean flag = false; // 标志是否找到待删除节点
        while (true){
            if (temp == null){ //已经到链表的最后
                break;
            }
            if (temp.next.no == no){
                //找到的待删除节点的前一个节点
                flag = true;
                break;
            }
            temp = temp.next; // temp后移,遍历
        }
        if (flag){//找到
            //可以删除
            temp.next = temp.next.next;
        }else {
            System.out.printf("要删除的%d 节点不存在\n",no);
        }
    }
    //显示链表[遍历]
    public void list(){
        //判断链表是否为空
        if (head.next == null){
            System.out.println("链表为空");
            return;
        }
        //因为头结点不能动,我们需要一个赋值遍历来遍历
        HeroNode temp = head.next;
        while (true){
            //判断是否到链表的最后
            if (temp == null){
                break;
            }
            //输出节点的信息
            System.out.println(temp);
            //将temp后移
            temp = temp.next;
        }
    }
    //
}

//定义头结点HeroNode,每个HeroNode 对象就是一个节点
class HeroNode {
    public int no;
    public String name;
    public String nickname;
    public HeroNode next;//指向下一个节点

    //构造器
    public HeroNode(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 + '\'' +
                '}';
    }
}

To be more specific, go to the link below

Java LinkedList | Rookie Tutorial (runoob.com)

Guess you like

Origin blog.csdn.net/weixin_46511995/article/details/125629784