大话数据结构:线性表(2)

原创 2016年05月30日 21:04:10

1.线性表的链式存储结构

1.1 顺序存储结构不足的解决办法

线性表的顺序存储结构最大的缺点是插入和删除时需要移动大量数据,这显然就需要消耗时间。本节讨论的链式存储结构可以很好滴解决这个问题。

线性表的链式存储结构的特点是用一组任意的存储单元存储线性表的数据元素,这些存储单元可以使连续的,也可以是不连续的。这就意味着,这些数据元素可以存在内存未被占用的任意位置。
以前的顺序结构中,每个数据元素只需要存数据元素的信息就可以了。现在链式结构中,除了要存数据元素信息外,还要存储它的后继元素的存储地址。
因此,为了表示每一个数据元素a(i)与其直接后继数据元素a(i+1)之间的逻辑关系。对数据a(1)来说,除了存储其本身的信息之外,还需存储一个指示其直接后继的信息(即直接后继的存储位置)。我们把存储数据元素信息的域称为数据域;把存储直接后继位置的域称为指针域。指针域中存储的信息称为指针或链。这两部分信息组成元素a(i)的存储映像,称为结点。如果每个结点只包含一个指针域,叫做单链表。单链表正是通过每个节点的指针域将线性表的数据元素按其逻辑次序连接在一起,如图所示:

对于线性表来说,总要有头有尾,链表也不例外。我们把链表中第一个结点的存储位置叫做头指针,那么整个链表的存取就必须是从头指针开始进行了。之后的每一个结点,其实就是上一个的后继指针指向的位置。最后有意义的是讨论最后一个结点的指针指向问题,暂时规定,线性链表的最后一个结点指针为“空”(NULL)

有时,我们为了更加方便地对链表进行操作,会在单链表的第一个结点前附设一个结点,称为头结点。头结点的数据域可以不存储任何信息,头结点的指针域存储指向第一个结点的指针,如图所示:

2.单链表操作

2.1 单链表的读取

在线性表的顺序存储结构中,我么要计算任意一个元素的存储位置时容易的。但是在单链表中,由于第i个元素到底在哪?没办法一开始就知道,必须从头开始找。
获得链表第i个数据的算法思路:
(1)声明一个结点p指向链表第一个结点,初始化j从1开始;
(2)当j<i时,就遍历链表,让p的指针向后移动,不断指向下一结点,j累加1;
(3)若到链表末尾p为空,则说明第i个元素不存在;
(4)否则查找成功,返回结点p的数据。
代码实现如下:
Status GetElem( LinkList* L, int i, ElemType* e)
{
      int j;
      LinkList p; //声明一节点p
      p = L->next; //让p指向链表L的第一个节点
      j = 1;
      while ( p && j<i)  //p不为空 或者计数器j还没有等于i时,循环继续
      {
             p = p->next; //让p指向下一个结点
             ++j;
       }
       if (!p || j>1i)
              return ERROR;
       *e = p->data;
       return OK;
}
说白了,就是从头开始找,知道第i个元素为止。由于这个算法的时间复杂度取决于i的位置,当i=1时,则不需要遍历,第一个就取出数据了,而当i = n时,则遍历n-1次就可以了,因此最坏情况的时间复杂度是O(n)。
由于单链表的结构中没有定义表长,所以不能事先知道要循环多少次,因此也就不方便使用for来控制循环。其主要核心思想就是“工作指针后移”。

2.2 单链表的元素插入

单链表的元素插入用不着惊到其他结点,只需要让s->next和p->next的指针做一点改变即可。

s->next = p->next;
p->next =s;

单链表第i个数据插入节点的算法思路:
(1)声明一结点p指向链表第一个结点,初始化j从1开始;
(2)当j<i时,就遍历链表,让p的指针向后移动,不断指向下一结点,j累加1;
(3)若到链表末尾p为空,则说明第i个元素不存在;
(4)否则查找成功,在系统中生成一个空节点s;
(5)将数据元素e赋值给s->data;
(6)单链表的插入标准语句s->next=p->next;p->next = s;
(7)返回成功。
实现代码算法如下:
Status ListInsert ( LinkList *L, int i, ElemType e)
{
       int j;
       LinkList p,s;
       p = *L;'
       j = 1;
       while( p && j<i)
       {
            p = p->next;
            ++j;
       }
       if ( !p || j>1)
             return ERROR;
       s = (LinkList)malloc(sizeof(Node));
        s->data = e;
        s->next = p->next;
        p->next = s;
        return OK;
}

2.3 单链表的元素删除

设存储元素a(i)的结点为q,要实现将节点q删除单链表操作,其实就是将他的前几结点的指针绕过,指向它的后继结点即可,如图所示:

这里需要做的只有一步,p->next = p->next->next,用q来取代p->next,删除语句可以写成:
q=p->next;
p->next = q->next;
单链表第i个数据删除节点的算法思路:
(1)声明一个结点p指向链表第一个结点,初始化j从1开始;
(2)当j小于i时,就遍历链表,让p的指针向后移动,不断指向下一个结点,j累加1;
(3)若到链表末尾p为空,则说明第i个元素不存在;
(4)否则查找成功,将预删除的结点p->next赋值给q;
(5)单链表的删除标准语句p->next=q->next;
(6)将q结点中的数据赋值给e,作为返回;
(7)释放q结点;
(8)返回成功。
实现代码算法如下:
Status ListDelete( LinkList* L, int i, ElemType* e)
{
      int j;
      LinkList p,q;
      p = *L;
      j = 1;
      while( p->next || j<i )
      {
            p = p->next;
            ++j;
       }
       if ( !(p->next) || j>i)
             return ERROR;
       q=p->next;
       p->next=q->next;
       *e = q->data;
       free(q);
       return OK;
}
版权声明:本文为博主原创文章,未经博主允许不得转载。 举报

相关文章推荐

大话数据结构3线性表

1、线性表:零个或多个数据元素的有限序列 2、线性表元素的个数n(n > 0)定义为线性表的长度,当n=0时,称为空表 3、线性表的抽象数据类型: ADT 线性表 Data 线性表的数据对象...

大话数据结构5线性表(续2)

1、单链表的读取:   获取链表第i个数据的算法思路:   1、声明一个结点p指向链表的第一个结点,初始化j从1开始;   2、当j   3、若到链表末尾p为空,则说明第i个元素不存在;  ...

精选:深入理解 Docker 内部原理及网络配置

网络绝对是任何系统的核心,对于容器而言也是如此。Docker 作为目前最火的轻量级容器技术,有很多令人称道的功能,如 Docker 的镜像管理。然而,Docker的网络一直以来都比较薄弱,所以我们有必要深入了解Docker的网络知识,以满足更高的网络需求。

【大话数据结构】线性表:顺序表和链表

线性表(List):零个或多个数据元素的有限序列。线性表数据总体分为两种结构,顺序存储结构,和链式存储结构。

大话数据结构-线性表-静态链表

我的微信号:quick_snail,希望能互相交流,互相学习 像JAVA,C#这一类语言,它们没有指针,并启用了对象引用机制,所以从某个角度也实现了指针的某些作用。静态链表的作用就是给一些没有指针...

大话数据结构-线性表-链式表

上一节说的顺序表是分配实际物理内存连续的存储区域用来存取的,而链式表是逻辑上连续的表,它们之间通过一个next指针指向下一个结点,即一个节点保存了下一个节点的地址 先看她的结构定义 基础讲解:...

《数据结构实验2》--线性表

#include #include #define MaxSize 50 typedef char elemtype; typedef struct node {     elemtype...

数据结构(第2章: 线性表)

线性表

数据结构基础(2)-------------线性表

1.线性表顺序存储结构的优点:一是无需为元素之间的逻辑关系而增加额外的存储空间;二是可以迅速的取表中任意位置的元素。其缺点为:一是插入和删除需要移动大量的元素;二是线性表需要固定的存储空间,不适用于线...

数据结构学习-线性表(2)

问题描述:编写一个程序exp2-2.cpp,实现单链表的各种基本运算(假设单链表的元素类型为char),并在此基础上完成如下功能: (1)初始化单链表h; (2)采用尾插法依次插入元素a,b,c,...

线性链表-数据结构(2)

一、解析 之所以叫线性,是因为逻辑结构上面是以顺序的存储的。而链的原因是因为在物理的存储结构上面保存后面元素的地址 。数据结构书上对应页码P27-31。 二、存储结构 //int...
返回顶部
收藏助手
不良信息举报
您举报文章:深度学习:神经网络中的前向传播和反向传播算法推导
举报原因:
原因补充:

(最多只允许输入30个字)