数据结构与算法——顺序表

1. 什么是线性结构? 

  1. 线性结构作为最常用的数据结构,其特点是数据元素之间存在一对一的线性关系。
  2. 线性结构拥有两种不同的存储结构,即顺序存储结构和链式存储结构。顺序存储的线性表称为顺序表,顺序表中的存储元素是连续的,链式存储的线性表称为链表,链表中的存储元素不一定是连续的,元素节点中存放数据元素以及相邻元素的地址信息。
  3. 线性结构中存在两种操作受限的使用场景,即队列和栈。栈的操作只能在线性表的一端进行,就是我们常说的先进后出(FILO),队列的插入操作在线性表的一端进行而其他操作在线性表的另一端进行,先进先出(FIFO),由于线性结构存在两种存储结构,因 此队列和栈各存在两个实现方式。

2. 线性结构中都包含什么内容? 

      1.  顺序表: 将元素顺序地存放在一块连续的存储区里,元素间的顺序关系由它们的存储顺序自然表示

      2. 链表: 将元素存放在通过链接构造起来的一系列存储块中

3. 什么是顺序表?顺序表的分类? 

 按照我们的习惯,存放东西时,一般是找一块空间,然后将需要存放的东西依次摆放,这就是顺序存储。计算机中的顺序存储是指在内存中用一块地址连续的空间依次存放数据元素,用这种方式存储的线性表叫顺序表其特点是表中相邻的数据元素在内存中存储位置也相邻,如下图:

4. 完成动态顺序表的以下操作: 

// 动态的顺序表 
typedef int DataType; 
typedef struct SeqList 
{ 
DataType* _array; 
int _capacity; // 顺序表的总大小 
int _size; // 顺序表中有效元素的个数 
}SeqList, *PSeq; 

//typedef struct SeqList SeqList; 
//typedef struct SeqList* PSeqList; 

// 顺序表的初始化 
void SeqListInit(PSeq ps, int capacity); 

// 在顺序表的尾部插入值为data的元素 
void SeqListPushBack(PSeq ps, DataType data); 

// 删除顺序表最后一个元素 
void SeqListPopBack(PSeq ps); 

// 在顺序表的头部插入值为data的元素 
void SeqListPushFront(PSeq ps, DataType data); 

// 删除顺序表头部的元素 
void SeqListPopFront(PSeq ps); 

// 在顺序表pos位置插入值为data的元素 
void SeqListInsert(PSeq ps, int pos, DataType data); 

// 删除顺序表中pos位置上的元素 
void SeqListErase(PSeq ps, int pos); 

// 在顺序表中查找值为data的元素,找到返回该元素在顺序表中的下标,否则返回-1 
int SeqListFind(PSeq ps, DataType data); 

// 检测顺序表是否为空,如果为空返回非0值,非空返回0 
int SeqListEmpty(PSeq ps); 

// 返回顺序表中有效元素的个数 
int SeqListSize(PSeq ps); 

// 返回顺序表的容量大小 
int SeqListCapacity(PSeq ps); 

// 将顺序表中的元素清空 
void SeqListClear(PSeq ps); 

// 删除顺序表中第一个值为data的元素 
void SeqListRemove(PSeq ps, DataType data); 

// 销毁顺序表 
void SeqListDestroy(PSeq ps); 

// 顺序表的扩容 
void CheckCapacity(PSeq ps); 

顺序表头文件:

#pragma once
#pragma once

#define ListSize 100      //线性表的最大长度
typedef int DataType;

typedef struct
{
	DataType data[ListSize];   //用数组存储线性表中的元素
	DataType length;           //顺序表的长度
}SeqList, *PSeqList;

void InitList(PSeqList L);  //顺序表的初始化操作
int LengthList(PSeqList L); //求顺序表的长度
int GetData(PSeqList L, int i); //返回数据表中第i个元素的值
int InsList(PSeqList L, int i, DataType e);   //在顺序表的第i个位置插入元素
int DelList(PSeqList L, DataType i, DataType* e); //删除顺序表L的第i个数据元素
int Locate(PSeqList L, DataType e); //查找数据元素e在表中的位置
void PushFront(PSeqList L, DataType e); //头插,在表头插入元素e
void PopFront(PSeqList L);    //头删,删除表中的第一个元素
void PushBack(PSeqList L, DataType e);  //尾插,在表尾插入元素e
void PopBack(PSeqList L); //尾删,删除表尾元素
void ClearList(PSeqList L);  //清空顺序表
int EmptyList(PSeqList L);   //判断顺序表是否为空
void PrintList(PSeqList L);  //打印表中元素

顺序表.c文件

#include <stdio.h>
#include "SeqList.h"

int k = 0;  //全局变量,用于作部分操作的循环变量
//初始化顺序表
void InitList(PSeqList L)
{
	if (L == NULL)
	{
		return;
	}
	L->length = 0;
}

//求顺序表的长度

int LengthList(PSeqList L)
{
	if (L == NULL)
	{
		return 0;
	}
	return L->length;
}

//返回数据表中第i个元素的值
int GetData(PSeqList L, int i)
{
	if (L->length < 1 || (L->length > LengthList(L)))
	{
		return 0;
	}
	//数据元素的序号从1开始,数组下表从0开始,第i个元素对应的数组下标为i-1;
	return L->data[i - 1];
}

//在L中第i个位置,插入新的数据元素e

int InsList(PSeqList L, int i, DataType e)
{

	//判断插入位置是否合法
	if (i < 1 || L->length >(LengthList(L) + 1))
	{
		printf("插入位置不合法!\n");
		return 0;
	}
	//判断顺序表是否已满
	else if (L->length >= ListSize)
	{
		printf("顺序表已满,不能插入!\n");
		return 0;
	}
	else
	{
		for (k = i; k <= L->length; k--)
		{
			L->data[k + 1] = L->data[k];
		}
		L->data[i - 1] = e;
		L->length++;   //数据表的长度加1
		return 1;
	}
	return 0;
}

//删除L的第i个数据元素

int DelList(PSeqList L, DataType i, DataType* e)
{
	if (L->length < 1)
	{
		printf("表为空!\n");
		return  0;
	}
	*e = L->data[i - 1];
	for (k = i; k < L->length; k++)
	{
		L->data[k - 1] = L->data[k];
	}
	L->length--;
	return *e;
}

//查找e在表中的位置

int Locate(PSeqList L, DataType e)
{
	for (k = 0; k < L->length; k++)
	{
		if (L->data[k] == e)
		{
			//k为e对应的数组下标,在表中对应序号应为k+1
			return k + 1;
		}
	}
	return 0;
}

//头插,在表头插入元素e

void PushFront(PSeqList L, DataType e)
{
	if (L->length == ListSize)
	{
		printf("顺序表已满,不能插入!\n");
	}
	//将表中元素依次后移一位
	for (k = L->length; k > 0; k--)
	{
		L->data[k] = L->data[k - 1];
	}
	//插入元素
	L->data[0] = e;
	L->length++;
}

//头删,删除顺序表中的第一个元素,把顺序表中的元素依次往前移动一位

void PopFront(PSeqList L)
{
	if (EmptyList(L))
	{
		printf("顺序表为空,不能插入!\n");
	}
	for (k = 1; k <= L->length - 1; k++)
	{
		L->data[k - 1] = L->data[k];
	}
	L->length--;
}

//尾插
void PushBack(PSeqList L, DataType e)
{
	if (L->length == ListSize)
	{
		printf("顺序表已满,不能插入!\n");
	}
	L->data[L->length] = e;
	L->length++;
}


//尾删
void PopBack(PSeqList L)
{
	if (EmptyList(L))
	{
		printf("表为空!\n");
	}
	L->length--;

}

//清空顺序表
void ClearList(PSeqList L)
{
	L->length = 0;
}

//判断表是否为空

int EmptyList(PSeqList L)
{
	if (L->length == 0)
	{
		return 1;
	}
	return 0;
}

//打印表中元素

void PrintList(PSeqList L)
{
	if (EmptyList(L))
	{
		printf("表为空!\n");
		return;
	}
	for (k = 0; k < L->length; k++)
	{
		printf("%-3d", L->data[k]);
	}
	printf("\n");
}
#include <Windows.h>
#include "SeqList.h"

int main()
{
	SeqList L;
	DataType data;
	//初始化顺序表
	InitList(&L);
	//在表中插入元素
	printf("依次在表中插入元素(1,2,3,4,5):\n");
	InsList(&L, 1, 1);
	InsList(&L, 2, 2);
	InsList(&L, 3, 3);
	InsList(&L, 4, 4);
	InsList(&L, 5, 5);

	//打印表中元素
	printf("表中元素有:\n");
	PrintList(&L);
	//头插
	printf("在表头依次插入元素,6,7:\n");
	PushFront(&L, 6);
	PushFront(&L, 7);
	//尾插
	printf("在表尾依次插入元素,8,9:\n");
	PushBack(&L, 8);
	PushBack(&L, 9);
	printf("表中元素有:\n");
	PrintList(&L);
	//头删
	printf("头删一个元素:\n");
	PopFront(&L);
	//尾删
	printf("尾删一个元素:\n");
	PopBack(&L);
	//输出表中第4个元素值
	PrintList(&L);
	printf("表中第4个元素值为:\n%d\n", GetData(&L, 4));
	//查找表中第 i个元素的位置
	printf("元素2在表中的位置为:\n");
	printf("%d\n", Locate(&L, 2));
	//删除表中第2个元素对应的值
	printf("删除表中第2个元素:%d\n", DelList(&L, 2, &data));
	printf("顺序表的长度为:%d\n", LengthList(&L));
	printf("表中元素为:\n");
	PrintList(&L);
	//printf("删除的元素值为:%d\n", data);
	//清空顺序表
	ClearList(&L);
	PrintList(&L);
	system("pause");
	return 0;
}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值