第三章 线性表---链式存储结构(双向链表)

双向链表(double linked list)是在单链表的每个结点中,再设置一个指向其前驱结点的指针域。结点都有两个指针域,一个指向直接后继,另一个指向直接前驱。


实例:


链表——双向链表

现在分析添加的情况
已经有1号英雄和5号英雄,现在要添加3号英雄

此时cur指向了1号英雄,hero指向3号英雄
cur指向1号英雄,发现cur的下一个是5号英雄,大于要添加的3号英雄
分析图

过程

(1)让3号英雄指向5号英雄,即把这个①号线搭起来
$hero->next=$cur->next; 
//$cur指向1号英雄,$cur->next指向5号英雄
(2)然后再搭pre这根线,让3号英雄的pre指向1号英雄,即把这个②号线搭起来
$hero->per=$cur;
(3)然后让5号英雄的pre指向3号英雄,即把这个③号线搭起来
$cur->next->pre=$hero;
//$cur->next指向5号英雄,$cur->next->pre为5号英雄指向1号英雄,即图中⑥号线
//此时⑥号线就断掉了,原来的5号英雄的pre是指向1号英雄的,现在指向了3号英雄
(4)让1号英雄指向3号英雄,即把这个④号线搭起来
$cur->next=$hero;
//此时⑤号线就断掉了,原来的$cur->next是指向5号英雄的,现在指向了3号英雄

改进:不严密的地方,可以和前面的进行合并的
添加英雄,把添加时是空链表和不是空链表的情况,合并到一起了
现在考虑:要添加的人就在末尾

有一个head和1号人物,要添加的是6号人物
此时cur指向1号人物,

当按照原先的代码执行,既下面这段代码,会有一些小问题的
$hero->next=$cur->next;
$hero->pre=$cur;
$cur->next->pre=$hero;
$cur->next=$hero;
执行
(1)$hero->next=$cur->next; 
此时cur指向1号人物,1号人物此时是最后的一个节点,$cur->next就是空了,那么$hero->next=$cur->next; 此时这句话就没有意义了,因为$hero->next本身就是空啊,你再赋给它空,没有意义,干脆这句话此时就不执行了。所以要加一个一个判断条件,即$cur->next不等于空,执行$hero->next=$cur->next; 才有价值
if($cur->next!=null){
$hero->next=$cur->next;
}
(2)$hero->pre=$cur; 
这句话还是很有价值的,如下图所示,把①号线搭起来了
(3)
$cur->next->pre=$hero;
此时cur指向1号人物,$cur->next就是空了,空的pre就没意义了,所有也要和上面的(1)一样,加判断
if($cur->next!=null){
$cur->next->pre=$hero;
}
(4)$cur->next=$hero;
这句是有意义的,如下图所示,把②号线搭起来了

如果前面的代码修改成了如下的代码:
if($cur->next!=null){
$hero->next=$cur->next;
}
$hero->pre=$cur;
if($cur->next!=null){
$cur->next->pre=$hero;
}
$cur->next=$hero;

就和前面的一个if判断语句不谋而合了

即在doubleLink.php中的这段代码
if($cur->next==null){ //如果是,就说明是空链表,添加第一个英雄
$cur->next=$hero;
//这样就首尾相连了
$hero->pre=$cur;
}else{...

都是在说当$cur->next为空的时候,就执行
$cur->next=$hero;
$hero->pre=$cur;

代码不是一步到位的,优化前进


======
此时删除英雄就不需要辅助节点了
分析图

当要删除的节点在最后的时候,还需要判断下

此时$cur->next本身就是空了,所有要加判断了
$cur->pre->next=$cur->next; //这个就相当于把1号节点的next置空了,这个没错
所以要这样:
if($cur->next!=null){
$cur->next->pre=$cur->pre;
}
$cur->pre->next=$cur->next;
这样执行的话,把上图中的蓝线就去掉了,这样6号英雄就访问不到了,6号英雄出列了,因为我们是从表头开始找的,$cur-next就访问不到6号英雄节点了,6号英雄指向别人是没有用的,★关键★是没有人指向它。

时间: 2025-01-14 17:17:27

第三章 线性表---链式存储结构(双向链表)的相关文章

第三章 线性表---链式存储结构(循环链表)

将单链表中终端结点的指针端由空指针改为指向头结点,就使整个单链表形成一个环,这种头尾相接的单链表称为单循环链表,简称循环链表(circular linked list) 结构模型

线性表—链式存储结构

链式存储结构就是一环扣一环的线性结构,好像链条中的每一个人都只知道下一个人的地址,只有从前往后顺序查找才能找到第 j 个人. 链式结构的好处是在插入和删除时不需要移动插入位置后面的元素,但要找到要插入和删除的元素的位置还是得像顺序存储结构一样查找,但这个查找还有所不同,顺序存储结构支持我们使用二分查找之类的方法进行查找插入以及删除的位置,至于链式结构感觉似乎没法使用二分法类似的方法(充分利用有序这一条件进行查找) 链式存储结构适合于插入删除操作比较多的场合,比如飞机航班的乘客信息,至于学校的学生

(源代码见大话数据结构)线性表—链式存储结构->单链表的删除ListDelet(*L,i,*e)

Status ListDelet(LinkList *L,int i,ElemType *e) { int j=1; LinkList p,s; p=*L; while(p&&j<i) { p=p->next; j++; } if(!p||j>i) return ERROR; s=p->next; *e=s->data; p->next=s->next; free(s); return OK; } 个人理解:建立一个新结点可以作为(i-1)个结点的

线性表—链式存储结构—单链表的创建CreasteListHead(*L,int n)-&gt;头插法

void CreasteListHead(LinkList *L,int n) { int i; LinkList p; srand(time(0)); *L=(LinkList)malloc(sizeof(Node)); (*L)->next=NULL;//优先级->大于* !!!!!!!!!!!!! for(i=0;i<n;i++) { p=(Node *)malloc(sizeof(Node)); p->data=rand()%100+1;//1~100之间的数包括一百所以+

数据结构之线性表——链式存储结构之单链表(php代码实现)

<?php /**  *  * 1. 类LNode用作创建单链表时,生成新的节点.  * 2. 类SingleLinkList用于创建单链表以及对单链表的一些操作方法(实例化此类就相当于创建了一个空链表)  * 3. CreateListHead: 具有$num个数据元素的单链表的创建--头插法  * 4. CreateListTail: 具有$num个数据元素的单链表的创建--尾插法  * 5. DestroyList: 销毁单链表  * 6. ClearList:清空单链表  * 7. Li

线性表-&gt;链式存储-&gt;循环链表

文字描述 循环链表是另一种形式的链式存储结构.它的特点是表中最后一个结点的指针域指向头结点,整个链表形成一个环.由此,从表中任一结点出发均可找到表中其他结点. 示意图 算法分析 插入.删除.查找等同单链表. 代码实现 1 // 2 // Created by lady on 19-1-27. 3 // 4 5 #include <stdio.h> 6 #include <stdlib.h> 7 8 //线性表的单向循环链表存储结构 9 typedef struct ElemType

数据结构之第二章线性表之链式存储

1~~特点:逻辑上相邻的元素,他的物理位置不一定相邻,其实几乎是不像邻的.表中的元素只能顺序访问,插入,删除等操作只需修改指针而不需要移动元素,存储空间利用率高,表的容量可以动态变化.适合个数变化大的情况. 2--链式存储`的存储结构 typedef struct Node{ int data; struct Node *next; }NODE,*PNODE; 3~~线性表的基本操作 (1)线性表的的  插表头  建立算法 ” 插表头“方式得到的线性链表,元素存储的顺序和输入顺序相反,这与栈的特

数据结构-线性表-链式存储

由于顺序表的插入.删除操作需要移动大量的元素,影响了运行效率,由此引入了线性表的链式存储. 链式存储线性表时,不需要使用地址连续的存储单元,即它不要求逻辑上相邻的两个元素在物理位置上也相邻,它是通过“链”建立起数据元素之间的逻辑关系. 因此,对线性表的插入.删除不需要移动元素,而只需要修改指针. 线性表的链式存储又称为单链表,它是指通过一组任意的存储单元来存储线性表中的数据元素.为了建立起数据元素之间的线性关系,对每个链表结点,除了存放元素自身的信息之外,还需要存放一个指向其后继的指针.单链表结

数据结构之线性表-链式存储之单链表(一)

本人文笔较差,语文从来不及格,基础不好,写此类文章仅供自己学习,理解队列及其他知识,高手大神请略过.参考书籍 <数据结构与算法分析-Java语言描述 1.1 单链表简介 线性表的最大的缺点就是插入和删除操作需要移动大量的元素,这是它在内存中的连续存储结构造成的.为了弥补这2个缺点,就出现了链表,即线性表的链式存储. 链表是由一系列的几点组成,这些节点不必在内存中相连.这就意味着元素可以存在内存未被占用的任意位置.如图 这个存储可以想象成元素在内存中成三维空间存储,他们之间可没有像数组那样的下标标