线性表
1. 什么是线性表?
线性表,全名为线性存储结构。使用线性表存储数据的方式可以这样理解,即“把所有数据用一根线儿串起来,再存储到物理空间中”。
所谓“一对一”的关系是指,一个元素只有一个前驱和一个后继,而且元素的内容是相同的,比如去图书馆占位置就是在一片连续的空间占一定大小的位置,可以不从开始占,选一个风水好的地方,但如果用书包和笔等东西来占位置就是不行的,因为元素不一样。
线性表的存储方式分为线性和非线性,如上文所说,线性存储方式就是在内存空间中开辟一段连续的空间,物理上相邻,逻辑上也相邻,可以用数组来实现,称之为顺序存储链表。
具体c实现可如下代码所示:
- 首先是定义数据结构:
typedef int ElemType;
typedef struct{
ElemType *elem; //存储空间的基地址
int length; //当前线性表的长度
int listsize; //当前分配的存储容量
} SqList;
- 然后是初始化,创建线性表。
//创建线性表
int InitList(SqList &L)
{
L.elem = (ElemType *)malloc(LIST_INIT_SIZE * sizeof(ElemType)); //开辟一个空间,并把这块存储空间的基地址赋给elem
if(!L.elem)
{
return -1;
}
L.length = 0;
L.listsize = LIST_INIT_SIZE;
return 0;
}
- 在线性表中插入元素:
在线性表中插入元素,就相当于排队时有人从前面插队,所谓一个萝卜一个坑,有人在前面插队,那后面的人就被迫要往后移动一个“坑位”。
值得注意的是,线性表的下标是从“1”开始的,而存储位置的下标是从“0”开始的。即线性表第i个元素存储在第i-1个下标位置。
LOC(a_(i+1)) = LOC(a_i) + c
LOC(a_i) = LOC(a_1) + (i-1)*c
其中 c 是指数据元素所占存储单元,比如 int 是 32位 4个字节
// 插入元素
int ListInsert(SqList &L,int i,ElemType e)
{
//判断插入位置的合法性
if (i<1 || i>L.length+1) return -1;
//判断存储空间是否够用
if (L.length > L.listsize)
{
ElemType* newbase = (ElemType*)realloc(L.elem,(L.listsize + LISTINCREMENT)*sizeof(ElemType));
if(!newbase) return -1; //存储空间分配失败
L.elem = newbase;
L.listsize += LISTINCREMENT;
}
//插入操作
ElemType *q,*p; //定义两个指针变量
q = &(L.elem[i-1]); //q为插入位置,i是从1开始的
for(p=&(L.elem[L.length-1]);p >= q;--p) //从ai到an-1依次后移,注意后移操作要从后往前进行
{
*(p+1) = *p;
}
*q = e; //插入位置赋值
++L.length; //表长加1
return 0;
}
- 获取元素操作
int main(int argc,char **argv)
{
SqList list;
InitList(list);
int n=10;
//添加10个数字给线性表list
for(int i=0;i<10;i++)
{
ListInsert(list,i+1,i+1);