线性表的顺序存储——数据结构

线性表——数据结构

线性表的定义

线性表(List):零个或多个数据元素的有限序列。

元素之间是有序的,若存在多个元素,则第一个元素无前驱,最后一个元素无后继,其他每个元素都有且只有一个前驱和后继。

线性表的顺序存储

指的是用一段地址连续的存储单元依次存储线性表的数据元素。

顺序存储结构

#define MAXSIZE 20 //初始存储空间分配量
typedef int Type;
typedef struct
{
	Type data[MAXSIZE]; //数组存储元素
	int length; //线性表当前长度
}SqList;

顺序结构的操作

获取元素操作

即返回线性表L中第i个位置的元素,只要i在数组下标的范围内,就是把数组第i-1个下标的值返回。

#define TRUE 1
#define FALSE 0
//获取元素操作
int GetElem(SqList L, int i, Type *e)
{
	if (L.length == 0)//线性表为空
		return FALSE;
	if (i < 1 || i > L.length)//i不在范围内
		return FALSE;
	*e = L.data[i - 1];//数组下标从0开始,线性表第i个位置元素的下标为i-1
	return TRUE;
}
插入操作

即在线性表L的第i个位置插入新元素e,只要插入的位置合理,从最后一个元素开始向前到第i个元素位置,分别将它们都向后移动一个位置,将插入元素填入位置i处。

//插入操作
int ListInsert(SqList *L, int i, Type e)
{
	int j;
	if (L->length == MAXSIZE)//线性表已满
		return FALSE;
	if (i<1 || i>L->length)//插入位置不合理
		return FALSE;`
	if (i <= L->length)//插入位置不在表尾
	{
		for (j = L->length - 1; j >= i - 1; j--)
		{
			L->data[j + 1] = L->data[j];//插入位置后的元素都往后移动一位
		}
	}
	L->data[i - 1] = e;//插入新元素
	L->length++;//表长加一
	return TRUE;
}
删除操作

即删除线性表L第i个位置的元素,只要删除位置合理,从删除位置开始到最后一个元素,分别将它们都向前移动一个位置。

//删除操作
int ListDelete(SqList *L, int i)
{
	int j;
	if (L->length == 0)//线性表为空
		return FALSE;
	if (i<1 || i>L->length)//删除位置不合理
		return FALSE;
	if (i < L->length)//删除位置不在表尾
	{
		for (j = i; j < L->length; j++)
		{
			L->data[j - 1] = L->data[j];//将删除位置后的元素前移一个位置
		}
	}
	L->length--;//表长减一
	return TRUE;
}
线性表顺序存储的优缺点
  1. 优点

    不需要为表示表中元素之间的逻辑关系而增加额外的存储空间;

    可以快速的存取表中任意位置的元素;

  2. 缺点

    插入和删除操作需要移动大量元素;

    当线性表长度变化较大时,难以确定存储空间的容量;

动态数组实现线性表的顺序存储
#include<stdio.h>
#include<stdlib.h>
#include<assert.h>

typedef int SLDataType;
// 顺序表的动态存储
typedef struct SeqList
{
	SLDataType* array; // 指向动态开辟的数组
	int size;    // 有效数据个数
	int capicity;  // 容量空间的大小
}SeqList;

// 顺序表初始化
void SeqListInit(SeqList* psl)
{
	assert(psl);
	psl->array = NULL;
	psl->capicity = 0;
	psl->size = 0;
}
// 顺序表销毁
void SeqListDestory(SeqList* psl)
{
	assert(psl);
	free(psl->array);
	psl->array = NULL;
	psl->capicity = psl->size = 0;
}
// 顺序表打印
void SeqListPrint(SeqList* psl)
{
	assert(psl);
	for (int i = 0; i < psl->size; i++)
	{
		printf("%d ", psl->array[i]);
	}
	printf("\n");
}
// 检查空间,如果满了,进行增容
void CheckCapacity(SeqList* psl)
{
	assert(psl);
	if (psl->size == psl->capicity)
	{
		int newcapicity = psl->capicity * 2;
		psl->array = (SLDataType*)realloc(psl->array, sizeof(SLDataType)*newcapicity);
		psl->capicity = newcapicity;
	}
}
// 顺序表尾插
void SeqListPushBack(SeqList* psl, SLDataType x)
{
	assert(psl);
	SeqListInsert(psl, psl->size, x);
}
// 顺序表尾删
void SeqListPopBack(SeqList* psl)
{
	assert(psl);
	SeqListErase(psl, psl->size);
}
// 顺序表头插
void SeqListPushFront(SeqList* psl, SLDataType x)
{
	assert(psl);
	SeqListInsert(psl, 0, x);
}
// 顺序表头删
void SeqListPopFront(SeqList* psl)
{
	assert(psl);
	SeqListErase(psl, 0);
}
// 顺序表查找
int SeqListFind(SeqList* psl, SLDataType x)
{
	assert(psl);
	for (int i = 0; i < psl->size; i++)
	{
		if (psl->array[i] == x)
		{
			return i;
		}
	}
	return -1;
}
// 顺序表在pos位置插入x
void SeqListInsert(SeqList* psl, int pos, SLDataType x)
{
	assert(psl);
	assert(pos<=psl->size);
	CheckCapacity(psl);//检查线性表是否已满,若满了则进行扩容操作
	int end = psl->size;
	while (end > pos)
	{
		psl->array[end] = psl->array[end - 1];
		end--;
	}
	psl->array[pos] = x;
	psl->size++;
}
// 顺序表删除pos位置的值
void SeqListErase(SeqList* psl, int pos)
{
	assert(psl);
	assert(pos<psl->size);
	int start = pos + 1;
	while (start < psl->size)
	{
		psl->array[start - 1] = psl->array[start];
		start++;
	}
	psl->size--;
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值