线性表:零个或多个数据元素的有限序列。
当线性表元素的个数为0时,称为空表。
若元素存在多个,则第一个元素无前驱,最后一个元素无后继,其他每个元素有且只有一个前驱和后继。
线性表的抽象数据类型
ADT 线性表List
Data
线性表的数据对象集合为{a1,a2,a3,....an},每个元素的类型均为DataType。数据元素之间的关系时一对一的关系。
Operation
- InitList(*L); // 初始化操作:建立一个空的线性表L。
- ListEmpty(L); //若线性表为空,返回ture ; 若线性表不为空,返回false ;
- ClearList(L); //将线性表清空。
- GetElem(L,i,*e); //将线性表L中的第i个位置元素值传回给e
- LocateElem(L,e); //在线性表L中找与e值相等的元素,如果成功,返回该元素咋爱表中序号;如果不成功,返回0;
- ListInset(*L,i,e); //在线性表L中第i个位置插入新元素e
- ListDelete(*L,i,e); //删除线性表L中的第i个位置元素,并用e返回其值。
- ListLength(L) ; //返回线性表L的元素个数
endADT
上述基本操作时最基本的,还会有复杂的个性化操作。
线性表的线性存储定义
先来说以下线性表的两种物理结构的第一种----顺序存储结构
它指的是用一段连续的存储单元依次存储线性表的数据元素。
我们先来看一下线性表顺序存储结构的结构代码。
#define MAXTURE 20
typedef int ElemType;//ElemType类型根据实际情况而定,这里假设是int
typedef struct
{
ElemType data[MAXTURE];//数组存储数据元素,最大值为MAXSIZE
int length;//线性表当前长度
}SqList; //相当于定义了这样一个结构的结构变量:顺序结构的线性表
注意:
数据长度是指存放线性表的存储空间的长度。一般不变。
线性表的长度指的是线性表中数据元素的个数。随着插入删除会变化。
顺序存储结构的插入与删除
- 插入
思路:将要插入的元素e插到线性表的第i个位置。如果插入位置不合理,返回异常;如果线性表的长度大于等于数组长度,则抛出异常或动态增容。
从最后一个元素开始向前遍历到第i个位置,分别将它们都向后移动一个位置。将要插入的元素填入第i个位置;表长加一。
Status ListInsert(SqList* L, int i, ElemType e) //status 是函数的返回类型
{
int k;
if (L->length == MAXTURE)//顺序线性表已满:在任何时刻,线性表的长度应该小于数组的长度
return ERROR;
if (i<1 || i>L->length + 1)//插入位置异常 :如果插在最后一个位置后面就是length +1
return ERROR;
if (i <= L->length)//如果插入的数据元素不在表尾:需要将第i个位置空出来,这个循环就是做这个工作
{
for (k = L->length - 1; k >= i - 1; k--)
L->data[k + 1] = L->data[k];//将最后一个元素赋值给它的后面那个元素
}
L->data[i - 1] = e;//将元素e放到第i个位置,下标为i-1;
L->length++;//表长加1
return OK;
}
- 删除
思路:如果删除位置不合理,抛出异常;取出删除的元素;从删除元素位置开始遍历到最后一个元素位置,分别将他们向前移动一个位置;表长减1;
Status ListDelete(SqList* L, int i, ElemType* e)
{
int k;
if (L->length == 0)//如果当前表长为0,那么无元素可删 返回错误
return ERROR;
if (i<1 || i>L->length)
return ERROR;
*e = L->data[i - 1];//将被删除的元素,赋值给e ;e是指针,所以用解引运算符来取指向e位置的值
if (i < L->length)//如果删除的不是表尾的元素,那么都要元素移动
{
for (k = i; k < L->length; k++)
{
L->data[k - 1] = L->data[k];//从第i+1个元素起,向前移一个元素
}
}
L->length--;//表长减1
return OK;
}