版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
链表1单链表(SinglyLinkedList)特点
每个元素(表项)由结点(Node)构成,结点由两部分组;线性结构
结点可以不连续存储表可扩充2单链表的存储映像3单链表中的插入与删除插入
第一种情况:在第一个结点前插入
newNode→Next=first;first=newNode;(插入前)(插入后)
firstnewNodenewNodefirst4算法:voidInsertFront(LNode*&H,constElemTypee){
LNode*p;p=newLNode;
if(p==NULL){
cout<<“分配失败!”;exit(1);}
pdata=e;pnext=Hnext;
Hnext=p;}5
(插入前)(插入后)
第二种情况:在链表中间插入
newNode→Next=p→Next;
p→Next=newNode;newNodepnewNodep6算法:voidInsert(LNode*&H,ElemTypee){
LNode*p,*q,*s;s=newLNode;
if(s==NULL){
cout<<“分配失败!”;exit(1);}
sdata=e;q=H;p=Hnext;
7
第三种情况:在链表末尾插入
newNode→Next=p→Next;
p→Next=last=newNode;(插入前)(插入后)newNodenewNodelastplastp8算法:voidInsertRear(LNode*&H,constElemTypee){
LNode*p;p=newLNode;
if(p==NULL){
cout<<“分配失败!”;exit(1);}
pdata=e;pnext=NULL;
LNode*q=H;}while(qnext!=NULL)q=qnext;qnext=p;}9删除第一种情况:删除表中第一个元素第二种情况:删除表中或表尾元素在单链表中删除含ai的结点10int
List::Remove(int
i){//在链表中删除第i个结点
Node
*p=first,*q;int
k=0;while(p!=NULL&&k<
i-1)
{p=p→Next;k++;}//找第i-1个结点
if(p==NULL
||
p→Next==NULL){
cout<<“无效的删除位置!\n”;return0;
}if(i==0){//删除表中第1个结点
q=first;
//q保存被删结点地址
p=first=first→Next;//修改first
}
11
else{//删除表中或表尾元素
q=p→Next;
p→Next=q→Next;//重新链接
} if(q==last)last=p; //可能修改last
k=q→data;deleteq;
//删除q
return
k; }12带表头结点的单链表表头结点位于表的最前端,本身不带数据,仅标志表头。设置表头结点的目的是统一空表与非空表的操作,简化链表操作的实现。非空表
空表0ana1firstlastfirst0last13在带表头结点的单链表第一个结点前插入新结点
newNode→Next=p→Next; if(p→Next
==NULL)last=newNode;
p→Next=newNode;14
q=p→Next;
p→Next=q→Next;deleteq;if(p→Next
==NULL)last=p;从带表头结点的单链表中删除第一个结点15
初始化单链表
向单链表的表头插入结点
在单链表的表尾插入结点建立带有头结点的单链表求单链表的长度判断单链表是否是空表
遍历单链表从单链表中查找给定值的元素取单链表中第i个结点的数据销毁单链表删除带有头结点的单链表中等于给定值的元素
插入一个元素到有序单链表中,使其仍保持有序16voidTraverseList(LNode*H){
LNode*p=Hnext;while(p!=NULL){
cout<<pdata<<‘‘;p=pnext;}}17voidInitList(LNode*&H){H=newLNode;
if(H==NULL){
cout<<“分配失败!”;exit(1);}Hnext=NULL;}18
最后一个结点的指针域的指针又指回第一个结点循环链表a1a2
…an判别链表中最后一个结点的条件不再是“后继是否为空”,而是“后继是否为头结点”。19ai-1aies->right=p->right;p->right=s;s->right->left=s;s->left=p;psai-1ai插入双向链表20ai-1删除aiai+1p->right=p->right->right;p->right->left=p;pai-121习题一2.5线性表两种存储结构的比较:关键词:空间---溢出时间---随机访问22单链表的类模板类模板将类的数据成员和成员函数设计得更完整、更灵活。类模板更易于复用。在单链表的类模板定义中,增加了表头结点。23template<classType>int
List<Type>::Length()const{//求单链表的长度
ListNode<Type>
*p=first→Next;
//检测指针p指示第一个结点
int
count=0;
while
(p!=NULL){//逐个结点检测
p=p→Next;count++;}
returncount;}24template<classType>ListNode<Type>*List<Type>::Find(Typevalue){//在链表中从头搜索其数据值为value的结点
ListNode<Type>
*p=first→Next;
//检测指针p
指示第一个结点
while(p!=NULL&&p→data!=value)
p=p→Next;
return
p;//p
在搜索成功时返回找到的结点地址
//p
在搜索不成功时返回空值}25template<classType>ListNode<Type>
*List<Type>::Find(int
i){//在链表中从头搜索第i个结点,不计头结点
if(i<-1
)
return
NULL;
if(i==-1)return
first; //i
应
0
ListNode<Type>
*p=first→Next;
int
j=0;
while(p!=NULL&&j<i)//j=i
停
{p=p→Next;j=j++;}
returnp; }26template<classType>intList<Type>::Insert(Type
value,
int
i){//将含value的新元素插入到链表第i个位置
ListNode<Type>
*p=Find(i-1);
//p
指向链表第i-1个结点
if(p==NULL)
return0;
ListNode<Type>
*newNode=//创建结点
GetNode
(value,
p→Next);
if(p→Next==NULL)last=newNode;
p→Next=newNode;//重新链接
return1;}27template<classType>Type*List<Type>::Remove(int
i){//从链表中删去第i
个结点
ListNode<Type>*p=Find(i-1),*q;
if(p==NULL||
p→Next
==NULL)
return
NULL;
q=p→Next;
p→Next=q→Next;//重新链接
Type
value=newType(q→data);
if(q==last)last=p;
deleteq;
return
&value;}28template<classType>Type
*List<Type>::Get(int
i){//提取第i
个结点的数据
ListNode<Type>
*p=Find(i);
//p
指向链表第i
个结点
if(p==NULL
||
p==first)
returnNULL;
elsereturn
&
p→data;}29链表的游标类(Iterator)游标类主要用于单链表的搜索。游标类的定义原则:
Iterator类是List类和ListNode类的友元类。
Iterator对象引用已有的List类对象。
Iterator类有一数据成员current,记录对单链表最近处理到哪一个结点。
Iterator类提供若干测试和搜索操作30表示链表的三个类的模板定义
enum
Boolean
{False,True};template<classType>class
List;template<classType>classListIterator;template<classType>class
ListNode
{//表结点friendclass
List<Type>;
friendclass
ListIterator<Type>; public:………
private:
Typedata;
ListNode<Type>
*Next;};31template<classType>classList
{//链表类public:………private:
ListNode<Type>
*first,*last;};template<classType>class
ListIterator{public:
ListIterator
(const
List<Type>
&l)
:
list(l),current(l.first)
{}
//构造函数:引用链表l,表头为当前结点32
BooleanNotNull();
//检查链表中当前指针是否非空
BooleanNextNotNull();//检查链表中下一结点是否非空
ListNode
<Type>*First();
//返回链表表头指针
ListNode
<Type>
*Next();
//返回链表当前结点的下一个结点的地址private:
constList<Type>
&list;//引用已有链表
ListNode<Type>*current;//当前结点指针}33链表的游标类成员函数的实现template<classType>BooleanListIterator<Type>::NotNull
(){//检查链表中当前元素是否非空
if(current!=NULL)return
True;
elsereturn
False;}currentcurrent情况1返回True
情况2返回False34template<classType>BooleanListIterator<Type>::NextNotNull(){//检查链表中下一元素是否非空
if(current!=NULL&&
current→Next
!=NULL)
return
True;
elsereturnFalse;}currentcurrent情况1返回True
情况2返回False35template<classType>ListNode<Type>*ListIterator<Type>::First(){//返回链表中第一个结点的地址
if(list.first→Next
!=NULL){
current=list.first;return¤t→data;}
else{current=NULL;return
NULL;}}list.firstcurrent约定链表中没有表头结点36template<classType>ListNode<Type>*ListIterator<Type>::Next(){//返回链表中当前结点的下一个结点的地址
if(current!=NULL
&&
current→Next
!=NULL){
current=current→Next;
return¤t→data;
}
else{current=NULL;returnNULL;}}currentcurrent37利用游标类(iterator)计算元素的和int
sum(const
List<int>
&l){
ListIterator<int>
li
(l);
//定义游标对象,current指向li.first
if(!li.NotNull()
)return0;
//链表为空时返回0
int
retval=*li.First()→data;//第一个元素
while(li.nextNotNull
())//链表未扫描完
retval+=*li.Next()→data;//累加
return
retval;}38静态链表结构利用数组定义,运算过程中存储空间大小不变分配节点:
j=avil;avil
=A[avil].Next;释放节点:A[i].Next=avil;avil=i;39循环链表(CircularList)循环链表是单链表的变形。循环链表最后一个结点的Next指针不为0(NULL),而是指向了表的前端。为简化操作,在循环链表中往往加入表头结点。循环链表的特点是:只要知道表中某一结点的地址,就可搜寻到所有其他结点的地址。40循环链表的示例带表头结点的循环链表
41template<classType>class
CircList;template<classType>class
CircListNode
{friendclass
CircList;public:
CircListNode
(Type
d=0,
CircListNode<Type>
*next=NULL):
data(d),Next(next){}//构造函数private:
Type
data;
CircListNode<Type>
*Next;}
循环链表类的定义42template<classType>classCircList
{public:
CircList
(Type
value);
~CircList();
int
Length()const;
BooleanIsEmpty
()
{return
first→Next==first;
}
BooleanFind(constType&value);
Type
getData
()const;
void
Firster
(){current=first;}
BooleanFirst();
BooleanNext();
43
BooleanPrior(); void
Insert(constType&value);
void
Remove(); private:
CircListNode<Type>
*first,*current,*last;};插入44用循环链表求解约瑟夫问题约瑟夫问题的提法
n
个人围成一个圆圈,首先第1个人从1开始一个人一个人顺时针报数,报到第m个人,令其出列。然后再从下一个人开始,从1顺时针报数,报到第m个人,再令其出列,…,如此下去,直到圆圈中只剩一个人为止。此人即为优胜者。45例如n=8m=346约瑟夫问题的解法#include<iostream.h>#include“CircList.h”Template<Type>voidCircList<Type>::Josephus(int
n,
int
m){
Firster
();
for(int
i=0;
i<n-1;
i++){
//执行n-1次
for(int
j=0;
j<m-1;
j++)Next();
cout
<<“出列的人是”<<
getData
()<<endl;//数m-1个人
Remove();//删去
}47}void
main(){
CircList<int>clist;
int
n,m;
cout<<“输入游戏者人数和报数间隔:”;
cin
>>n>>m;
for(int
i=1;
i<=n;
i++)
clist.insert(i);
//形成约瑟夫环
clist.Josephus(n,m);
//解决约瑟夫问题}48多项式及其相加在多项式的链表表示中每个结点增加了一个数据成员Next,作为链接指针。优点是:多项式的项数可以动态地增长,不存在存储溢出问题。插入、删除方便,不移动元素。49多项式(polynomial)类的链表定义struct
Term{
int
coef;
int
exp;
Term(int
c,
int
e){coef=c;exp=e;
}};
classPolynomial {
List<Term>poly;//构造函数
friend
Polynomial
&
operator+(Polynomial&,
Polynomial&);
//加法};
50多项式链表的相加AH=1-10x6+2x8+7x14BH=-x4+10x6-3x10+8x14+4x1851
Polynomial&operator+(Polynomial&ah,
Polynomial&
bh
){
//多项式加法,结果由ah表头结点指示
ListNode<Term>*pa,*pb,*pc,*p;
ListIterator<Term>Aiter
(ah.poly);
ListIterator<Term>Biter(bh.poly
);
//建立两个多项式对象
Aiter、Biterpa=pc=Aiter.First
();//
ah
检测指针
pb=p=Biter.First();
//
bh
检测指针
pa=Aiter.Next
();
pb=Biter.Next();
//pa,
pb
越过表头结点
delete
p;52while(Aiter.NotNull
()
&&
Biter.NotNull
())switch(compare(pa→exp,pb→exp
))
{case‘=’: //pa指数等于pb指数
pa→coef=pa→coef+pb→coef; p=pb;
pb=Biter.Next();
deletep; if(!pa→coef
){//指数相加结果为0
p=pa;pa=Aiter.Next
();
delete
p;}else{//指数相加结果不为0
pc→Next=pa;pc=pa;//链入结果链
pa=Aiter.Next
();
}
53
break;case‘>’: //pa指数大于pb指数
pc→Next=pb;pc=pb;
pb=Biter.Next();break;case‘>’: //pa指数小于pb指数
pc→Next=pa;pc=pa;
pa=Aiter.Next
();
}if(Aiter.NotNull
())
pc→Next=pa; else
pc→Next=pb;}
54双向链表(DoublyLinkedList)双向链表是指在前驱和后继方向都能游历(遍历)的线性链表。双向链表每个结点结构:
前驱方向
后继方向双向链表通常采用带表头结点的循环链表形式。55结点指向
p==
p→lLink→rLink==p→rLink→lLink
非空表
空表56双向循环链表类的定义template<classType>classDblList;template<classType>class
DblNode
{friendclass
DblList<Type>;private:
Typedata;//数据
DblNode<Type>
*lLink,*rLink;//指针
DblNode(Typevalue,//构造函数
DblNode<Type>
*left,
DblNode<Type>
*right)
:
data(value),
lLink
(left),
rLink
(right){}57
DblNode(Typevalue)
:
data(value),
lLink
(NULL),
rLink
(NULL){} };template<classType>class
DblList
{public:
DblLIst(
TypeuniqueVal
); ~DblList
();
int
Length()const;
int
IsEmpty()
{
return
first→rNext==first;}
int
Find(constType&target);Type
getData
()const;58
void
Firster()
{current=first;}
int
First();
int
Next();
int
Prior();
intoperator!()
{
return
current!=NULL;
} void
Insert(constType&value); void
Remove(); private:
DblNode<Type>
*first,*current;};59搜索成功搜索不成功双向循环链表的搜索算法60template<classType>int
DblList<Type>::Find(constType&target){//在双向循环链表中搜索含target的结点,//搜索成功返回1,否则返回0。
DblNode<Type>
*p=first→rLink;
while(p!=first&&p→data!=target)
p=p→rLink; //循链搜索
if(p!=first){current=p;
return1;
}
return0;}61p→lLink=current; p→rLink=current→rLink; current→rLink=p;current=current→rLink; current→rLink→lLink=current;双向循环链表的插入算法非空表插入
空表插入62template<classType>void
DblList<Type>::Insert(constType&value){
if
(current==NULL)//空表情形
current=first→rLink=
new
DblNode
(value,first,first);
else{//非空表情形
current→rLink=new
DblNode
(value,current,current→rLink
);
current=current→rLink;}
current→rLink→lLink=current;}63current→rLink→lLink=current→lLink;current→lLink→rLink=current→rLink;双向循环链表的删除算法64template<classType>void
DblList<Type>::Remove(){
if(current!=NULL){
DblNode*temp=current;//被删结点
current=current→rLink; //下一结点
current→lLink=temp→lLink;//从链中摘下
temp→lLink→rLink=current;
delete
temp;
//删去
if(current==first)
if(
IsEmpty
())current=NULL;
else
current=current→rLink;
}}65其他双向循环链表的公共操作template<classType>DblList<Type>::DblLIst
(TypeuniqueVal){//双向循环链表的构造函数,创建表头结点
first=
new
DblNode<Type>(uniqueVal);
first→rLink=first→lLink=first;
current=NULL;}66template<classType>int
DblList<Type>::Length()const{//求双向循环链表的长度(不计表头结点)
DblNode<Type>*p=first→rLink;
int
count=0;
while(p!=first)
{p=p→rLink;
count++;
}
return
count;
}67template<classType>int
DblList<Type>::First(){
if(!IsEmpty())//跳过表头结点的第一个
{
current=first→rLink;
return1;
}
current=NULL;
return0;}template<classType>int
DblList<Type>::Next(){
if(current→rLink==first)
{
current=NULL;
return0;
}
current=current→rLink;
return1;}68template<classType>int
DblList<Type>::Prior(){
if(current→lLink==first)
{
current=NULL;
return0;
}
current=current→lLink;
return1;}
69稀疏矩阵在矩阵操作(+、-、*、/)时矩阵非零元素会发生动态变化,用稀疏矩阵的链接表示可适应这种情况。稀疏矩阵的链接表示采用正交链表:行链表与列链表十字交叉。行链表与列链表都是带表头结点的循环链表。用表头结点表征是第几行,第几列。70稀疏矩阵的结点
headdownnextright(a)表头结点(b)非零元素结点rightvaluedownheadrawcola[i][j]Falseij(c)建立a[i][j]结点
71稀疏矩阵的正交链表表示的示例72稀疏矩阵的链表表示的类定义enum
Boolean
{False,True};struct
Triple{introw,
col;
floatvalue;};class
Matrix;class
MatrixNode
{//矩阵结点定义friendclassMatrix;friendistream&operator>>(istream&,
Matrix&
); //矩阵输入重载函数private:
MatrixNode*down,*right;
//列/行链指针
Booleanhead;//结点类型73
Union
{Tripletriple;
MatrixNode*next;}
//矩阵元素结点(False)或链头结点(True)
MatrixNode
(Boolean,Triple*);
//结点构造函数
}MatrixNode::MatrixNode
(Booleanb,Triple*t){//矩阵结点构造函数
head=b;
//结点类型
if(b)
{right=next=this;}
else
triple=*t;}74typedef
MatrixNode*MatrixNodePtr;//一个指针数组,用于建立稀疏矩阵
class
Matrix{
friendistream&
operator>>(istream&,Matrix&);//矩阵输入public:
~Matrix(); //析构函数private:
MatrixNode*headnode;
//稀疏矩阵的表头};75用正交链表表示的稀疏矩阵的建立istream&
operator
>>(istream
&is,Matrix&matrix){
Triples;
int
p;
is>>s.row>>s.col>>s.value;
//输入矩阵的行数,列数和非零元素个数
if(s.row>s.col)p=s.row;
else
p=s.col;//取行、列数大者
matrix.headnode=
//整个矩阵表头结点
new
MatrixNode(False,
&s);
if
(!p){
//零矩阵时
matrix.headnode→right=matrix.headnode;
76
return
is;
}
MatrixNodePtr*H=
new
MatrixNodePtr(p);
//建立表头指针数组,指向各链表的表头
for(int
i=0;i<p;i++)
H[i]=
new
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 学校音乐室的空间设计与学生艺术素养培养
- 专业医师视角下的家属如何参与患者的护理工作
- 第7课《呼风唤雨的世纪》说课稿2024-2025学年统编版语文四年级上册
- Unit10 Great inventions (说课稿)-2023-2024学年沪教牛津版(深圳用)英语五年级下册
- 第一单元第三节 体验云上生活 说课稿 2024-2025学年川教版(2024)信息科技 七年级上册
- 2023-2024学年粤教版(2019)高中信息技术必修一《数据与计算》第五章第二节《数据的采集》说课稿
- 2025届高考语文补充背诵文言文阅读:《梦溪笔谈》说课稿
- 全国粤教版信息技术八年级下册第一单元第一课《计算机解决问题的基本过程》说课稿001
- Unit 1 Friendship-Section 3 说课稿 2024-2025学年沪教版英语七年级上册
- 全国山西经济版小学信息技术第三册第一单元活动12《动画的输出》说课稿
- 常用静脉药物溶媒的选择
- 当代西方文学理论知到智慧树章节测试课后答案2024年秋武汉科技大学
- 2024年预制混凝土制品购销协议3篇
- 2024-2030年中国高端私人会所市场竞争格局及投资经营管理分析报告
- GA/T 1003-2024银行自助服务亭技术规范
- 《消防设备操作使用》培训
- 新交际英语(2024)一年级上册Unit 1~6全册教案
- 2024年度跨境电商平台运营与孵化合同
- 2024年电动汽车充电消费者研究报告-2024-11-新能源
- 湖北省黄冈高级中学2025届物理高一第一学期期末考试试题含解析
- 上海市徐汇中学2025届物理高一第一学期期末学业水平测试试题含解析
评论
0/150
提交评论