数据结构学习笔记——顺序存储结构

来源:互联网 发布:中国软件国际地址 编辑:程序博客网 时间:2024/05/16 08:45

顺序表:用一组地址连续的存储单元一次存放线性表中的数据元素。
线性表的起始地址称为线性表的基地址
所有元素的存储位置均取决于第一个元素的存储位置。设a的存储地址为LOC(a),每个数据元素占l个存储地址,则第i个数据元素的地址为LOCai=LOCa1+(i1)l
也就是说只要知道顺序表首地址和每个数据元素所占地址单元的个数就可求出第i个数据元素的地址来,这也是顺序表具有按数据元素的序号随机存取的特点。

存取结构

存取结构存储结构是两个不同的概念
存取结构是在一个数据结构上对查找操作的时间性能的一种描述。
通常有两种存取结构:随机存取结构顺序存取结构

  • 随机存取结构:指在一个数据结构上进行查找的时间性能是O1。顺序表就是一种随机存取结构。
  • 顺序存取结构:指在一个数据结构上进行查找的时间性能是On。单链表就是一种顺序存取结构。

顺序映像的C语言描述

  • 静态分配
#define LISTSIZE 100 //存储空间最大分配量typedef struct{    ElemType elem[LISTSIZE];    int length; //当前长度}SqList;
  • 动态分配
#define LIST_INIT_SIZE 100#define LISTINCREMENT 10 //分配增量typedef struct{    ElemType *elem;//存储空间基址    int length;//当前长度    int listsize;//当前分配的存储容量(以sizeof(ElemType)为单位)}SqList;

插入操作

线性表的插入是指在表的第i(i的取值范围:1in+1)个位置上插入一个值为x的新元素,
插入后使原表长为 n的表:(a1a2...ai1aiai+1...an)成为表长为 n+1 表:(a1a2...ai1xaiai+1...an)
顺序表上完成这一运算则通过以下步骤进行:
① 将aian 顺序向下移动,为新元素让出位置;(注意数据的移动方向:从后往前依次
后移一个元素)
② 将 x 置入空出的第i个位置;
③ 修改表长。

Status ListInsert_Sq(SqList &L, int i, ElemType e) {  //   // 在顺序线性表L的第i个元素之前插入新的元素e,  // i的合法值为1≤i≤ListLength_Sq(L)+1  ElemType *p;  if (i < 1 || i > L.length+1) return ERROR;  // i值不合法  if (L.length >= L.listsize) {   // 当前存储空间已满,增加容量    ElemType *newbase = (ElemType *)realloc(L.elem,                  (L.listsize+LISTINCREMENT)*sizeof (ElemType));    if (!newbase) return ERROR;   // 存储分配失败    L.elem = newbase;             // 新基址    L.listsize += LISTINCREMENT;  // 增加存储容量  }  ElemType *q = &(L.elem[i-1]);   // q为插入位置  for (p = &(L.elem[L.length-1]); p>=q; --p) *(p+1) = *p;                                  // 插入位置及之后的元素右移  *q = e;       // 插入e  ++L.length;   // 表长增1  return OK;} // ListInsert_Sq

顺序表上的插入运算,时间主要消耗在了数据的移动上,在第i个位置上插入 x ,从 aian都要向下移动一个位置,共需要移动ni1个元素。

删除操作

线性表的删除运算是指将表中第 i (i 的取值范围为 :1in)个元素从线性表中去掉,
删除后使原表长为 n 的线性表:(a1a2...ai1ai+1...an)成为表长为 n-1 的线性表:(a1a2...ai1ai+1...an)
顺序表上完成这一运算的步骤如下:
① 将ai+1an顺序向上移动;(注意数据的移动方向:从前往后依次前移一个元素)
② 修改表长。

Status ListDelete_Sq(SqList &L, int i, ElemType &e) {  //   // 在顺序线性表L中删除第i个元素,并用e返回其值。  // i的合法值为1≤i≤ListLength_Sq(L)。  ElemType *p, *q;  if (i<1 || i>L.length) return ERROR;  // i值不合法  p = &(L.elem[i-1]);                   // p为被删除元素的位置  e = *p;                               // 被删除元素的值赋给e  q = L.elem+L.length-1;                // 表尾元素的位置  for (++p; p<=q; ++p) *(p-1) = *p;     // 被删除元素之后的元素左移  --L.length;                           // 表长减1  return OK;} // ListDelete_Sq

顺序表的删除运算与插入运算相同,其时间主要消耗在了移动表中元素上,删除第i个元素时,其后面的元素ai+1an都要向上移动一个位置,共移动了ni个元素。
顺序表的插入、删除需移动大量元素O(n);但在尾端插入、删除效率高O(1)

0 0