基础数据结构之一链表介绍
2011-06-06
链表(Linked list)是一种常见的基础数据结构,是一种线性表,但是并不会按线性的顺序存储数据,而是在每一个节点里存到下一个节点的指针(Pointer)。由于不必须按顺序存储,链表在插入的时候可以达到O(1)的复杂度,比另一种线性表顺序表快得多,但是查找一个节点或者访问特定编号的节点则需要O(n)的时间,而顺序表相应的时间复杂度分别是O(logn)和O(1)。
使用链表结构可以克服数组链表需要预先知道数据大小的缺点,链表结构可以充分利用计算机内存空间,实现灵活的内存动态管理。但是链表失去了数组随机读取的优点,同时链表由于增加了结点的指针域,空间开销比较大。
在计算机科学中,链表作为一种基础的数据结构可以用来生成其它类型的数据结构。链表通常由一连串节点组成,每个节点包含任意的实例数据(data fields)和一或两个用来指向明上一个/或下一个节点的位置的链接("links")。链表最明显的好处就是,常规数组排列关联项目的方式可能不同于这些数据项目在记忆体或磁盘上顺序,数据的存取往往要在不同的排列顺序中转换。而链表是一种自我指示数据类型,因为它包含指向另一个相同类型的数据的指针(链接)。链表允许插入和移除表上任意位置上的节点,但是不允许随机存取。链表有很多种不同的类型:单向链表,双向链表以及循环链表。
链表可以在多种编程语言中实现。像Lisp和Scheme这样的语言的内建数据类型中就包含了链表的存取和操作。程序语言或面向对象语言,如C/C++和Java依靠易变工具来生成链表。
单向链表
链表中最简单的一种是单向链表,它包含两个域,一个信息域和一个指针域。这个链接指向列表中的下一个节点,而最后一个节点则指向一个空值。
一个单向链表包含两个值: 当前节点的值和一个指向下一个节点的链接
一个单向链表的节点被分成两个部分。第一个部分保存或者显示关于节点的信息,第二个部分存储下一个节点的地址。单向链表只可向一个方向遍历。
链表最基本的结构是在每个节点保存数据和到下一个节点的地址,在最后一个节点保存一个特殊的结束标记,另外在一个固定的位置保存指向第一个节点的指针,有的时候也会同时储存指向最后一个节点的指针。一般查找一个节点的时候需要从第一个节点开始每次访问下一个节点,一直访问到需要的位置。但是也可以提前把一个节点的位置另外保存起来,然后直接访问。当然如果只是访问数据就没必要了,不如在链表上储存指向实际数据的指针。这样一般是为了访问链表中的下一个或者前一个(需要储存反向的指针,见下面的双向链表)节点。
相对于下面的双线链表,这种普通的,每个节点只有一个指针的链表也叫单向链表,或者单链表,通常用在每次都只会按顺序遍历这个链表的时候(例如图的邻接表,通常都是按固定顺序访问的)。
双向链表
一种更复杂的链表是"双向链表"或"双面链表"。每个节点有两个连接:一个指向前一个节点,(当此"连接"为第一个"连接"时,指向空值或者空列表);而另一个指向下一个节点,(当此"连接"为最后一个"连接"时,指向空值或者空列表)
一个双向链表有三个整数值: 数值, 向后的节点链接, 向前的节点链接
在一些低级语言中, XOR-linking 提供一种在双向链表中通过用一个词来表示两个链接(前后),我们通常不提倡这种做法。
双向链表也叫双链表。双向链表中不仅有指向后一个节点的指针,还有指向前一个节点的指针。这样可以从任何一个节点访问前一个节点,当然也可以访问后一个节点,以至整个链表。一般是在需要大批量的另外储存数据在链表中的位置的时候用。双向链表也可以配合下面的其他链表的扩展使用。
由于另外储存了指向链表内容的指针,并且可能会修改相邻的节点,有的时候第一个节点可能会被删除或者在之前添加一个新的节点。这时候就要修改指向首个节点的指针。有一种方便的可以消除这种特殊情况的方法是在最后一个节点之后、第一个节点之前储存一个永远不会被删除或者移动的虚拟节点,形成一个下面说的循环链表。这个虚拟节点之后的节点就是真正的第一个节点。这种情况通常可以用这个虚拟节点直接表示这个链表,对于把链表单独的存在数组里的情况,也可以直接用这个数组表示链表并用第0个或者第-1个(如果编译器支持)节点固定的表示这个虚拟节点。
循环链表
在一个 循环链表中, 首节点和末节点被连接在一起。这种方式在单向和双向链表中皆可实现。要转换一个循环链表,你开始于任意一个节点然后沿着列表的任一方向直到返回开始的节点。再来看另一种方法,循环链表可以被视为"无头无尾"。这种列表很利于节约数据存储缓存, 假定你在一个列表中有一个对象并且希望所有其他对象迭代在一个非特殊的排列下。
指向整个列表的的指针可以被称作存取指针。
用单向链表构建的循环链表
循环链表中第一个节点之前就是最后一个节点,反之亦然。循环链表的无边界使得在这样的链表上设计算法会比普通链表更加容易。对于新加入的节点应该是在第一个节点之前还是最后一个节点之后可以根据实际要求灵活处理,区别不大(详见下面实例代码)。当然,如果只会在最后插入数据(或者只会在之前),处理也是很容易的。
另外有一种模拟的循环链表,就是在访问到最后一个节点之后的时候,手工的跳转到第一个节点。访问到第一个节点之前的时候也一样。这样也可以实现循环链表的功能,在直接用循环链表比较麻烦或者可能会出现问题的时候可以用。
其它
链表中的节点不需要以特定的方式存储,但是集中存储也是可以的,主要分下面这几种具体的存储方法:
共用存储空间:链表的节点和其它的数据共用存储空间,优点是可以存储无限多的内容(不过要处理器支持这个大小,并且存储空间足够的情况下),不需要提前分配内存;缺点是由于内容分散,有时候可能不方便调试。
独立存储空间:一个链表或者多个链表使用独立的存储空间,一般用数组或者类似结构实现,优点是可以自动获得一个附加数据:唯一的编号,并且方便调试;缺点是不能动态的分配内存。当然,另外的在上面加一层块状链表用来分配内存也是可以的,这样就解决了这个问题。这种方法有时候被叫做数组模拟链表,但是事实上只是用表示在数组中的位置的下标索引代替了指向内存地址的指针,这种下标索引其实也是逻辑上的指针,整个结构还是链表,并不算是被模拟的(但是可以说成是用数组实现的链表)。
链表用来构建许多其它数据结构,如堆栈,行列和他们的衍生。
节点的数据域也可以成为另一个链表。通过这种手段,我们可以用列表来构建许多链性数据结构;这个实例产生于Lisp编程语言,在Lisp中链表是初级数据结构,并且现在成为了常见的基础编程模式。 有时候,链表用来生成联合数组,在这种情况下我们称之为联合数列。这种情况下用链表会优于其它数据结构,如自平对分查找树(self-balancing binary search trees)甚至是一些小的数据集合。不管怎样,一些时候一个链表在这样一个树中建立一个节点子集,并且以此来更有效率地转换这个集合。
相关推荐
数据结构之链表:深入解析单链表的创建与操作 在计算机科学中,数据结构是数据项的集合,它们之间存在一种或多种特定的关系,这些关系规定了数据的组织方式,以及对数据进行操作的方法。链表是一种线性数据结构,...
链表是一种基本的数据结构,它是一种非顺序存储结构,通过指针将各个节点连接起来,每个节点都包含了数据和指向下一个节点的指针。链表的优点是可以动态地增减节点,插入和删除节点的时间复杂度是O(1),但是访问第n...
链表是一种基础且重要的数据结构,它在计算机科学中扮演着至关重要的角色,尤其是在处理动态数据集合时。链表与数组不同,不依赖于连续的内存空间,而是通过节点之间的引用连接来存储数据。在本复习中,我们将深入...
双向链表是一种重要的线性数据结构,与常见的单向链表相比,它具有更丰富的操作能力。本文将深入探讨双向链表的概念、特点、实现方式以及在给定的“DoubleLink”压缩包中可能包含的相关功能。 双向链表(Doubly ...
双向链表是数据结构中的一种,尤其在处理需要前后移动元素的问题时,它的优势尤为突出。本篇文章将详细探讨双向链表的基本概念、结构以及实现,旨在帮助初学者理解并掌握这一重要知识点。 双向链表是一种线性数据...
双链表是一种重要的线性数据结构,它的每个元素(节点)都包含两部分:数据域和指针域。本实验将深入探讨双链表的概念、操作以及其实现。 双链表与单链表的主要区别在于,它在每个节点上不仅保存了指向下一个节点的...
链表是一种基础且重要的数据结构,它在计算机科学中扮演着关键角色,特别是在处理动态数据集合时。相较于数组,链表允许更灵活的内存管理,因为它不需要预先分配连续的存储空间。下面,我们将深入探讨链表的概念、...
在这个"数据结构之双向链表(完整版)"的资源中,你将找到关于双向链表的详细实现和实际应用。 双向链表的结构由一系列节点组成,每个节点包含数据元素和两个指针,一个指向前一个节点(prev),另一个指向后一个节点...
本实验“数据结构实验之链表合并”聚焦于如何有效地合并两个已排序的链表,这是一个常见的操作,特别是在处理动态数据集合时。下面我们将深入探讨这个主题。 链表是一种线性数据结构,与数组不同,它不连续存储元素...
在IT领域,数据结构是计算机科学的基础之一,它...在实际开发中,理解并熟练掌握这些基础数据结构和算法,能够优化程序性能,解决复杂问题。通过这个课设,你可以深入探究链表内部工作机制,锻炼逻辑思维和编程技巧。
链表作为一种基础的数据结构,广泛应用于各种算法和问题的解决,包括数学中的多项式运算。本主题将深入探讨如何利用链表来实现多项式的加法、减法和乘法操作。 首先,我们需要理解链表的基本概念。链表不同于数组,...
### 数据结构之链表详解 #### 一、链表基本概念 **链表**是一种常见的数据结构,它通过一组地址不连续的存储单元来存储线性表中的各个数据元素。链表中的每个元素称为**结点**,这些结点不仅包含实际的数据信息,...
在IT领域,数据结构是计算机科学中的核心概念之一,它涉及到如何有效地组织和存储数据,以便于算法的高效执行。线性表是数据结构中的一种基础类型,它是由n(n>=0)个相同类型元素构成的有限序列。在本话题中,我们...
根据给定的文件信息,我们可以总结出以下关于“数据结构中的链表插入...对于学习数据结构和算法的同学来说,掌握链表的插入是非常重要的基础之一。通过实践此类实验,可以帮助加深对链表这一数据结构的理解和应用能力。
总的来说,“数据结构之二叉树链表”项目提供了一种实用的方法,通过C++实现链表形式的二叉树,并展示了如何进行基本操作和遍历。这对于学习数据结构、提升编程技能,特别是理解和应用递归至关重要。熟悉这些概念和...
在编程领域,算法和数据结构是核心技术之一,对于学习编程和寻找工作的学生来说,掌握这些概念至关重要。"算法大全-面试题-链表-栈-二叉树-数据结构"这个压缩包文件提供了丰富的知识资源,旨在帮助学习者深入理解和...
### 数据结构之链表 #### 一、链表概述 链表是一种常用的数据结构,在计算机科学领域占有极其重要的地位。链表与数组等其他数据结构相比,在某些操作上具有显著的优势,尤其是在动态调整大小和频繁插入删除的情况...
在IT领域,数据结构是计算机科学的基础之一,它关乎如何高效地存储和处理数据。本文将深入探讨"合并有序链表"这一主题,这在单链表初学者中是非常重要的话题。链表作为一种非线性数据结构,与数组相比,具有更灵活的...