线性表之静态链表
1. 什么是静态链表
用数组描述的链表叫做静态链表,这种描述方法叫做游标实现法。
2. 用ADT来描述静态链表
ADT 静态链表
Data
- 静态链表元素通常为一个结构体,这个结构体包含数据域(data)和游>标域(cursor)。链表通过这样的结构体数组来定义。
静态链表需要预先分配一个较大的空间。在插入和删除操作中不需移>动元素,仅需修改游标,仍具有链式存储结构的主要优点- 对数组的第一个和最后一个元素作特殊处理,不存放数据:通常将第一个元素记录备用链表的开始位置,最后一个元素记录数据的开始位置。
- 什么是备用链表:由于静态链表用数组来实现,所以有存储空间限制。我们将静态链表的存储分为两个部分,一为已经存放有数据的数组元素,二为未使用的数据元素 即为备用链表。
- 数组下标为0的元素 即第一个元素的游标为备用链表的开头,数组下标为LENGTH-1 即数组的最后一个元素的游标存放链表(有数据的那一部分)的开头。
- 用游标值得0来表示链表的结尾。
- 当一个链表元素被删除时,该数组元素将并入备用链表
Operation
- InitList(*L):初始化操作,建立一个空的线性表L
- ListEmtpy(L):判断线性表是否为空,若线性表为空,返回true,否则返回false。
- ClearList(*L):将线性表清空
- GetElem(L,I,*e):将线性表L中的第i个位置元素值返回给e
- LocateElem(L,e):在线性表L中查找与给值e相等的元素,如果查找成功,返回该元素在表中序号表示成功,否则返回0表示失败(此处为伪代码,给人看,不给机器看,若是机器,应返回-1)
- ListInsert(*L,i,e):在线性表L中第i个位置插入新元素e
- ListDelete(*L,I,*e):删除线性表L中第i个位置元素,并用e返回其值
- ListLength(L):返回线性表的元素个数
……EndADT
3. 静态链表的定义
//SL:static list
#define SLMAX_LEN 10 //定义静态链表数据域的长度
typedef int DataTypeSL;
typedef unsigned int CurTypeSL;
typedef struct _StaticList {
DataTypeSL data;
CurTypeSL cur;
}StaticList[SLMAX_LEN], ComponentSL;
4. 静态链表的接口
#define _IsEmpty(ptr) (!(ptr)[SLMAX_LEN-1].cur)
#define _IsFull(ptr) (!(ptr)[0].cur)
#define _IsOnlyOne(ptr) ((ptr)[SLMAX_LEN-1].cur && !(ptr)[(ptr)[SLMAX_LEN-1].cur].cur)
bool InitStaticList(StaticList p);//初始化链表
CurTypeSL MallocSL(StaticList p);//分配存储
void FreeSL(StaticList p, CurTypeSL cursor);//回收存储
bool IsEmptySL(const StaticList p);//检测是否链表为空
bool IsFullSL(const StaticList p);//检测静态链表是否已满
//移动到链表最后一个元素,传入pos保存最后一个元素的下标,传入pos_prev保存倒数第二个元素的下标,pos可以为NULL,pos_prev也可以为NULL
bool MoveToEndSL(const StaticList p, CurTypeSL *pos, CurTypeSL *pos_prev);
//移动到链表中指定的位置(position)
//传入pos保存position元素的下标
//传入pos_prev保存position前一个元素的下标
//is_out_of_range保存该position是否超过链表的实际长度
//pos可以为NULL,pos_prev可以为NULL,is_out_of_range也可以为NULL
bool MoveToPosSL(const StaticList p, CurTypeSL position, CurTypeSL *pos, CurTypeSL *pos_prev, bool *is_out_of_range);
unsigned int GetLengthSL(const StaticList p);//获取链表的长度
unsigned int GetUpperBound();//获取静态链表存储数据个数的上限
bool InsertFrontSL(StaticList p, const DataTypeSL data);//链表前面插入一个元素
bool RemoveFrontSL(StaticList p);//前面删除一个元素
bool InsertBackSL(StaticList p, const DataTypeSL data);//后面插入一个元素
bool RemoveBackSL(StaticList p);//后面删除一个元素
bool InsertSL(StaticList p, CurTypeSL position, const DataTypeSL data);//任意位置插入一个元素
bool RemoveSL(StaticList p, CurTypeSL position);//任意位置删除一个元素
bool ReverseSL(StaticList p);//反转静态链表
//打印静态链表,用isOrigin指定是否打印静态链表的结构。false只打印数据,true则打印整个数组 显示静态链表的完整结构
void ShowStaticList(const StaticList p, bool isOrigin);
上述为笔者个人的设计方案,不是什么标准或是强制性的
5. 接口实现
完整代码:
https://yunpan.cn/crcgiPdMIEevN 访问密码 a641