链表是线性表的一种链式存储结构。
数组是线性表的顺序存储结构。
【线性表】
线性表中数据元素之间的关系是一对一的关系,即除了第一个和最后一个数据元素之外,其它数据元素都是首尾相接的。
【线性表的实现】
线性表有两种存储方式,
一种是顺序存储结构,我们常用的Array数组就是一种典型的顺序存储结构。
另一种是链式存储结构。链表LinkedList就是一种典型的链式存储结构
【链表和数组的存储特点】
数组必须在内存是连续的,因为数组是同一个数据格式,内存是对齐的。
好处:查找方便。随机读取。O(1)
坏处:增删方便不方便,数组是内存固定大小申请的。不能随意拓展。涉及到内存划分和对齐的原因。浪费内存。
链式存储结构就是两个相邻的元素在内存中可能不是相邻的。但是逻辑上是相邻的。
好处:链表增删是O(1)
每一个元素都有一个指针域,指针域一般是存储着到下一个元素的指针。这种存储方式的优点是定点插入和定点删除的时间复杂度为 O(1),不会浪费太多内存。添加元素的时候才会申请内存,删除元素会释放内存。
缺点:查找是O(N)
必须遍历呀。
-------------------------------------------------------------------------
编程实现
Python
class ListNode:
def __init__(self, val): #构造函数
self.val = val # 实例化的值
self.next = None #下一个结点对象 全部。只不过实际实现是通过内存地址索引再加上数据类型(即内存Bit长度)读取的
Java
public class ListNode {
public int val;
public ListNode next;
public ListNode(int val) {
this.val = val;
this.next = null;
}
}
【理解】
由于C和C++可以操作内存。所以可以看作是Node=value + *next(指向下一个Node)
所以我们可以看作是Node之间是通过node的内存地址来连接的。
模型是内存地址绳子串接Node
但是我们在python 和 java是没有指针操作的概念。
所以应该好的理解是 Node包含全部。
模型应该是大鱼吃小鱼的串接。我包含你。你包含他。一直下去。
【碎碎念】
一般来说好多书籍课本都是写作那种C的 绳子串接Node模型。个人觉得差意思。
因为链表的本质是Node的包含:即当前Node包含下一个Node。但是在实际机器实现的似乎是根据存储Node内存首地址再根据数据类型对应的内存长度(Bit位数)读取的。也就是本质是包含整个Node才对。大鱼吃小鱼的。
但是实际实现只能存储一个首地址呀 那么再默认配合数据类型的长度 ==等价变成== 整个Node啊。 这算是具体物理实现。
但是概念上大鱼吃小鱼的全部Node包办模型更方便理解。好比俄罗斯套娃一样。