一.链表的概念
链表是一种线性数据结构,其中元素通过"指针"或"引用"连接在一起
每个元素(称为节点)都包含两部分:
- 数据域:存储着节点的实际数据
- 指针域:存储下一个(或上一个)节点的内存地址
链表的基本结构如下:
节点1 节点2 节点3
+------+ +------+ +------+
| 数据 | | 数据 | | 数据 |
| A | | B | | C |
+------+ +------+ +------+
| 指针 | --> | 指针 | --> | 指针 | --> null
+------+ +------+ +------+
二.Java超详细代码实现
java
public class SinglyLinkedList{
private static class Node{
int value; // 节点的值
Node next; // 指向下一个节点的指针
public Node(int value, Node next) {
value = value;
next = next;
}
}
}
Node类的构造方法中出现的极大的问题:字段赋值错误(没有使用this关键字)
value = value;
next = next;
这两行代码实际上没有给成员变量赋值,而是将参数赋值给了自己(即局部变量覆盖,因为局部变量\参数和成员变量同名了,局部变量会遮蔽成员变量)
成员变量的this.value和this.next会保持默认值0和null(在Java中,类的成员变量也叫实例变量,如果没有显式初始化,则会被自动赋予一个"默认值"。这是Java虚拟机JVM保证的,目的是防止使用未初始化的内存)
默认值规则如下:
| 数据类型 | 默认值 |
|---|---|
byte |
0 |
short |
0 |
int |
0 |
long |
0L |
float |
0.0f |
double |
0.0d |
char |
'\u0000'(空字符) |
boolean |
false |
所有引用类型(如 Object, String, Node 等) |
null |
java
package algorithm.datastructure.linkedlist;
public class SinglyLinkedList{
Node head; // 头指针
// 静态内部类Node(节点不需要知道它属于哪个链表,只需要知道自己的value和next,和外部链表对象无关。因此用static修饰Node类)
// 用private修饰,其他文件无法访问Node类(对外隐藏实现细节)
private static class Node{
int value; // 节点的值
Node next; // 指向下一个节点的指针
// 带参构造方法
// 构造方法不能被被任何访问修饰符之外的关键字修饰,只能被public、protected、private修饰
// 这里主要理解构造方法为什么不能被static修饰:因为构造方法本质上是为一个新对象初始化状态,而static表示与对象无关只与类有关,两者矛盾
public Node(int value, Node next) {
this.value = value; // this关键字表示当前实例对象的引用(注意:this不能在static上下文中使用,因为静态方法\变量属于类,不属于任何该类的对象)
this.next = next; // 在内部类中,this指的是当前内部类自身(Node自己);若要访问外部类的this,需要用outerClassName.this
}
}
public void addFront(int value) {
head = new Node(value, head); // 这行代码能处理头指针为空和头指针不为空的两种情况
/*分析:
* 如果head为null,则向链表头部插入一个节点就是:新节点的next指针指向null,然后让头指针指向新节点
* 如果head不为null,则头插法:新节点的next指向head(即链表的第一个节点),再让第一个节点head指向新节点*/
}
public void loop() {
for (Node p = head; p != null; p = p.next) {
System.out.println(p.value);
}
// 或
// Node p = head;
// while (p != null) {
// System.out.println(p.value);
// p = p.next;
// }
}
}
java
package algorithm.datastructure.linkedlist;
public class Test1 {
public static void main(String[] args) {
SinglyLinkedList list = new SinglyLinkedList();
list.addFront(1);
list.addFront(2);
list.addFront(3);
list.addFront(4);
list.addFront(5);
list.loop();
}
}
输出:
java
5
4
3
2
1