链表结构Java

什么是链表

链表(LinkedList)是一种常见的数据结构,它由一系列节点(Node)组成,每个节点包含一个数据元素和一个指向下一个节点的指针。链表可以通过这个指针连接起来,形成一个链式结构。相比于数组,链表的插入和删除操作更加高效,但是访问元素的效率较低。

链表的基本操作

链表的基本操作包括插入节点、删除节点和遍历链表。

插入节点

在链表中插入一个节点,需要先找到插入位置,然后修改指针指向。

/** 在链表头部插入一个节点 */
public void addToHead(T data) {
    Node<T> newNode = new Node<>(data);
    newNode.next = head;
    head = newNode;
    size++;
}

/** 在链表尾部插入一个节点 */
public void addToTail(T data) {
    Node<T> newNode = new Node<>(data);
    if (isEmpty()) {
        head = newNode;
    } else {
        Node<T> current = head;
        while (current.next != null) {
            current = current.next;
        }
        current.next = newNode;
    }
    size++;
}

/** 在指定位置插入一个节点 */
public void insert(int index, T data) {
    if (index < 0 || index > size) {
        throw new IndexOutOfBoundsException("Index: " + index + ", Size: " + size);
    }
    if (index == 0) {
        addToHead(data);
    } else if (index == size) {
        addToTail(data);
    } else {
        Node<T> newNode = new Node<>(data);
        Node<T> current = head;
        for (int i = 0; i < index - 1; i++) {
            current = current.next;
        }
        newNode.next = current.next;
        current.next = newNode;
        size++;
    }
}

删除节点

在链表中删除一个节点,需要先找到要删除的节点,然后修改指针指向。

/** 删除头节点 */
public void deleteFromHead() {
    if (isEmpty()) {
        throw new NoSuchElementException("The LinkedList is empty.");
    }
    head = head.next;
    size--;
}

/** 删除尾节点 */
public void deleteFromTail() {
    if (isEmpty()) {
        throw new NoSuchElementException("The LinkedList is empty.");
    }
    if (size == 1) {
        head = null;
    } else {
        Node<T> current = head;
        while (current.next.next != null) {
            current = current.next;
        }
        current.next = null;
    }
    size--;
}

/** 删除指定位置的节点 */
public void delete(int index) {
    if (index < 0 || index >= size) {
        throw new IndexOutOfBoundsException("Index: " + index + ", Size: " + size);
    }
    if (index == 0) {
        deleteFromHead();
    } else if (index == size - 1) {
        deleteFromTail();
    } else {
        Node<T> current = head;
        for (int i = 0; i < index - 1; i++) {
            current = current.next;
        }
        current.next = current.next.next;
        size--;
    }
}

遍历链表

遍历链表即依次访问链表中的每个节点,并输出节点的值。

/** 遍历链表并输出节点的值 */
public void traverse() {
    Node<T> current = head;
    while (current != null) {
        System.out.print(current.data + " ");
        current = current.next;
    }
    System.out.println();
}

链表的应用

链表在实际应用中有许多用途,如实现栈、队列、图等数据结构,也可以用来解决一些具体的问题。

实现栈

栈(Stack)是一种后进先出(LIFO)的数据结构,可以使用链表来实现。

public class Stack<T> {
    private LinkedList<T> list;

    public Stack() {
        list = new LinkedList<>();
    }

    public void push(T data) {
        list.addToHead(data);
    }

    public T pop() {
        if (isEmpty()) {
            throw new NoSuchElementException("The Stack is empty.");
        }
        T data = list.getHead();
        list.deleteFromHead();
        return data;
    }

    public boolean isEmpty() {
        return list.isEmpty();
    }
}

实现队列

队列(Queue)是一种先进先出(FIFO)的数据结构,也可以使用链表来实现。