数据结构(C):玩转顺序表

news2024/12/24 9:56:07

🍺0.前言

        言C之言,聊C之识,以C会友,共向远方。各位博友的各位你们好啊,这里是持续分享数据结构知识的小赵同学,今天要分享的数据结构知识是顺序表,在这一章,小赵将会向大家展开聊聊顺序表。✊

🎷1.线性表

线性表 linear list n 个具有相同特性的数据元素的有限序列。 线性表是一种在实际中广泛使 用的数据结构, 常见的线性表:顺序表、链表、栈、队列、字符串...
线性表在逻辑上是线性结构,也就说是连续的一条直线。但是在物理结构上并不一定是连续的, 线性表在物理上存储时,通常以数组和链式结构的形式存储。

 也就是说我们今天要谈的顺序表就属于我们的线性表。

🎸2.顺序表

顺序表是用一段 物理地址连续 的存储单元依次存储数据元素的线性结构,一般情况下采用数组存 储。在数组上完成数据的增删查改。
顺序表一般可以分为:
1. 静态顺序表:使用定长数组存储元素。
2.动态顺序表:使用动态开辟的数组存储。

好了下面我们来看看究竟怎么样才是一个顺序表,其实很简单,小赵在这里给各位画个图

怎么样它的样子是不是非常的眼熟,没错我们的线性表其实就是我们的数组。那为什么有静态和动态之分呢?因为一个可以不断增长自己的内存,一个则是固定容量,那该如何实现呢?下面小赵将会带着大家去实现顺序表。

因为静态顺序表其实和动态的线性表差距不大,而且静态顺序表本身也并不常用(开大了浪费,开小了,不够),所以小赵在这里主要带着大家去实现我们的动态顺序表。

📀动态顺序表的实现

那么动态的顺序表该如何实现呢?在这里为了方便我们在后续知道什么时候该进行扩大我们的数组,我们就用我们的结构体去实现我们的线性动态表。

typedef int SeqDataType;
struct Seqlist
{
	SeqDataType* a;//指向动态开辟的数组
	int size;//顺序表已存元素个数
	int capacity;//顺序表容量
};

 那么这样当我们的size 等于我们的capacity的时候我们就可以对我们的数组进行扩容了。

那么对于我们的顺序表,光有这个是不够的,还要具备增删查改,初始化等等功能,下面带着大家一一来实现

💿初始化:

首先是初始化的操作

typedef struct Seqlist SL;
void InitSeq(SL* psl)
{
	assert(psl);//防止传入空指针
	psl->a = NULL;
	psl->capacity = 0;
	psl->size = 0;
}

💿检查容量是否满了,进行扩容

void SLCheckcapacity(SL* psl)
{
	assert(psl);
	if (psl->capacity == psl->size)
	{
		int newcapacity = (psl->capacity==0?4: psl->capacity *2);//如果原容量为零则返回4,其他返回原容量的两倍
		SeqDataType *tmp = (SeqDataType*)realloc(psl->a ,sizeof(SeqDataType) *newcapacity);//reallc新数组
		if (tmp == NULL)
		{
			perror("malloc failed");
			return;
		}
		psl->a = tmp;
		psl->capacity = newcapacity;
	}
}

💿插入:头插和尾插

这里的头插要稍微注意一下,就像我们站个队,忽然要我们在前面给个位子一样,那么我们是不是后面的人都要向后移动,那么如何向后移动呢,如果是从头移动,我们会发现下面的问题。

我们会发现我们前面的数字会盖住后面的数字,那么这里最后的办法就是后面向后移动,给出位子。

然后就可以顺利解决了。代码如下

void SLPushFront(SL* psl, SeqDataType x)
{
	assert(psl);
	SLCheckcapacity(psl);//检查容量
	int n = psl->size-1;
	while (n--);//将所有元素向后移动
	{
		psl->a[n + 1] = psl->a[n];
	}
	psl->a[0] = x;
	psl->size++;
}

 尾插就相对比较容易了。

void SLPushBack(SL* psl, SeqDataType x)
{
	assert(psl);
	SLCheckCapacity(psl);
	psl->a[psl->size++] = x;
}

💿删除:头删和尾删

这里的头删的思路和我们的头插的思路很像,只是这里是头边有空位

void SLPopFront(SL* psl)
{
	assert(psl);
	assert(psl->size);//防止元素个数为0
	int n = 1;
	while (n < psl->size)
	{
		psl->a[n-1] = psl->a[n];//把后面的往前移
        n++;
	}
	psl->size--;
}

尾删则相对容易些: 

void SLPopBack(SL* psl)
{
	assert(psl);
	assert(psl->size);//防止元素个数为0
	psl->size--;
}

💿查找:

int SLFind(SL* psl, SeqDataType x)
{
	assert(psl);
	int n = 0;
	while (n<psl->size)
	{
		if (psl->a[n] == x)//找到了返回对应位置
			return n;
		n++;
	}
	return -1;//找不到
}

💿销毁:

void SLDestory(SL* psl)
{
	assert(psl);
	free(psl->a);
	psl->a = NULL;
	psl->capacity = 0;
	psl->size = 0;
}

💿打印:

void SLPrint(SL* psl)
{
	assert(psl);
	int n = 0;
	while (n < psl->size)
	{
		printf("%d", psl->a[n]);
		n++;
	}
}

💿在某处插入和删除:

在某处的插入和删除对于逻辑的考察是有的,那么我们先看看如何进行插入:

比方说,我要在三这个位置进行插入操作,那么这个时候3,4,5这几个数字是不是要向后移动,那么其就很像我们的头删,都是从尾部开始向后移动,来完成的。

void SLInsert(SL* psl, int pos, SeqDataType x)
{
	assert(psl);
	assert(0 <= pos && pos <= psl->size);
	SLCheckcapacity(psl);
	int end= psl->size-1;
	while (end >= pos)
	{
		psl->a[end + 1] =psl->a[end];
		end--;
	}
	psl->a[pos] = x;
	psl->size++;
}

接下来是某个位置的删除,类比头删

void SLErase(SL* psl, int pos, SeqDataType x)
{
	assert(psl);
	assert(0 <= pos && pos < psl->size);
	int end = pos;
	while (end<psl->size-1)
	{
		psl->a[end] = psl->a[end+1];
		end++;
	}
	psl->size--;
}

 然后我们还可以用这两个代码改我们原本的头尾插,头尾删

void SLPushFront(SL* psl, SeqDataType x)
{
	SLInsert(psl, 0, x);
}
void SLPushBack(SL* psl, SeqDataType x)
{
	SLInsert(psl, psl->size, x);
}
void SLPopFront(SL* psl)
{
	SLErase(psl, 0);
}
void SLPopBack(SL* psl)
{
	SLErase(psl, psl->size-1);
}

 

💎6.结束语

好了小赵今天的分享就到这里了,如果大家有什么不明白的地方可以在小赵的下方留言哦,同时如果小赵的博客中有什么地方不对也希望得到大家的指点,谢谢各位家人们的支持。你们的支持是小赵创作的动力,加油。

如果觉得文章对你有帮助的话,还请点赞,关注,收藏支持小赵,如有不足还请指点,小赵及时改正,感谢大家支持!!! 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1638818.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

PotatoPie 4.0 实验教程(31) —— FPGA实现摄像头图像高斯滤波

什么是高斯滤波 高斯滤波是一种常见的图像处理技术&#xff0c;用于去除图像中的噪声和平滑图像。它的原理基于统计学中的高斯分布&#xff08;也称为正态分布&#xff09;。 在高斯滤波中&#xff0c;一个二维的高斯核函数被用来对图像中的每个像素进行加权平均。这个高斯核…

基于Java+SpringBoot+Mybaties-plus+Vue+elememt+hadoop + redis 医院就诊系统 设计与实现

一.项目介绍 前端&#xff1a;患者注册 、登录、查看首页、医生排班、药品信息、预约挂号、就诊记录、电子病历、处方开药、我的收藏 后端分为&#xff1a; 医生登录&#xff1a;查看当前排班信息、查看患者的挂号情况、设置患者就诊记录、电子病历、给患者开药和个人信息维护 …

LeetCode 11—— 盛最多水的容器

阅读目录 1. 题目2. 解题思路一3. 代码实现一4. 解题思路二5. 代码实现二 1. 题目 2. 解题思路一 暴力法&#xff0c;遍历所有可能的垂线对 ( i , j ) (i, j) (i,j)&#xff0c;求取最大面积&#xff1a; a r e a m i n ( h [ i ] , h [ j ] ) ∗ ( j − i ) area min(h[i]…

when to create a ViewRootImpl

when to create a ViewRootImpl when method setView is called: when method dispatchDetachedFromWindow is called:

2024年【起重机械安全管理】考试内容及起重机械安全管理操作证考试

题库来源&#xff1a;安全生产模拟考试一点通公众号小程序 起重机械安全管理考试内容根据新起重机械安全管理考试大纲要求&#xff0c;安全生产模拟考试一点通将起重机械安全管理模拟考试试题进行汇编&#xff0c;组成一套起重机械安全管理全真模拟考试试题&#xff0c;学员可…

ubuntu20.04安装nodejs并创建简单的node.js应用

一. 安装nodejs Node.js 为 Linux、Windows 和 macOS 提供了不同的软件包。您可以访问 Node.js 官方网站并选择与您的操作系统对应的下载链接。 第一步&#xff1a;打开官网下载源文件 中文网址:http://nodejs.cn/download/ 第二步&#xff1a;解压压缩包 tar -xvf node-v18.…

关于Spring Aop的通知类型

一、概述 1.1 通知类型 为了符合各种流程处理&#xff0c;通知类型提供了5种&#xff0c;可以对目标方法进行全方位处理&#xff0c;如下所示&#xff1a; 通知类型说明前置通知&#xff08;Before advice&#xff09;在某连接点之前执行的通知&#xff0c;但这个通知不能阻止…

【C语言】atoi和atof函数的使用

人生应该树立目标&#xff0c;否则你的精力会白白浪费。&#x1f493;&#x1f493;&#x1f493; 目录 •&#x1f319;知识回顾 &#x1f34b;知识点一&#xff1a;atoi函数的使用和实现 • &#x1f330;1.函数介绍 • &#x1f330;2.代码演示 • &#x1f330;3.atoi函数的…

Java | Spring框架 | 快速入门实战

一、Spring框架简介&#xff1a;为何选择Spring&#xff1f; Spring框架是一个开源的Java平台&#xff0c;它最初由Rod Johnson设计&#xff0c;并且首次发布于2003年。Spring使Java开发变得更加容易&#xff0c;它提供了一种更简洁、更强大、更易于测试的方式来构建Java应用。…

Debian操作系统的常用指令介绍

Debian是一个流行的Linux操作系统&#xff0c;以其稳定性和安全性而闻名。对于Debian用户来说&#xff0c;掌握一些基本的命令行指令是非常重要的&#xff0c;因为它们可以帮助你更高效地管理系统。在这篇博客中&#xff0c;我们将介绍一些在Debian系统中常用的指令及其功能。 …

【20】JAVASE-网络编程【从零开始学JAVA】

Java零基础系列课程-JavaSE基础篇 Lecture&#xff1a;波哥 Java 是第一大编程语言和开发平台。它有助于企业降低成本、缩短开发周期、推动创新以及改善应用服务。如今全球有数百万开发人员运行着超过 51 亿个 Java 虚拟机&#xff0c;Java 仍是企业和开发人员的首选开发平台。…

快速建站介绍

随着在线业务和电子商务的规模不断扩大&#xff0c;初创公司、个人网站和小型企业都需要快速地搭建自己的网站&#xff0c;以便更好地展示自己、推广产品和服务&#xff0c;并实现在线交易。快速建站已成为在线业务发展的一种主流方式&#xff0c;因为它能够快速地创建一个响应…

【C++】哈希的应用---布隆过滤器

目录 1、引入 2、布隆过滤器概念 3、选择哈希函数个数和布隆过滤器长度 4、布隆过滤器的实现 ①框架的搭建 ②设置存在 ③检查存在 ④不支持 reset 5、布隆过滤器计算误差 6、布隆过滤器的优缺点 ①布隆过滤器优点 ②布隆过滤器缺陷 7、布隆过滤器的实际应用 8、完…

腾锐D2000-8 MXM VPX,全国产,可广泛应用于边缘计算网关、入侵检测、VPN、网络监控等等应用领域

腾锐D2000-8 MXM VPX 1. 概述 XMVPX-108 是一款基于飞腾 D2000/8 处理器的低功耗逻辑运算和图形处理 VPX 刀片&#xff0c; 板贴 32GB DDR4 内存&#xff0c;搭载飞腾 X100 套片&#xff0c;满足通用 IO 接口功能。GPU 采用 MXM 小型插卡形式&#xff0c; 搭配 8GB 显卡。提供…

初识BootStrap

目录 前言: 1.Bootstrap的特点包括&#xff1a; 1.1响应式设计&#xff1a; 1.2组件丰富&#xff1a; 1.3易于定制&#xff1a; 1.4兼容性良好&#xff1a; 1.5强大的社区支持&#xff1a; 1.6一致的样式和布局&#xff1a; 1.7 插件和扩展性 2.初识Ajax: 2.1同步请求…

容器组_生命周期

&#x1f4d5;作者简介&#xff1a; 过去日记&#xff0c;致力于Java、GoLang,Rust等多种编程语言&#xff0c;热爱技术&#xff0c;喜欢游戏的博主。 &#x1f4d8;相关专栏Rust初阶教程、go语言基础系列、spring教程等&#xff0c;大家有兴趣的可以看一看 &#x1f4d9;Jav…

Linux用户权限管理与文件权限设定

一、相关概念 1、用户与角色分类 超级用户&#xff1a;拥有对系统的最高管理权限&#xff0c;默认是root用户。 普通用户&#xff1a;只能对自己目录下的文件进行访问和修改&#xff0c;具有登录系统的权限&#xff0c;例如www用户、ftp用户等。 虚拟用户&#xff1a;也叫“…

计算机408备考-数据结构重要知识点-数据结构的定义

请关注一下B站账号&#xff1a;谭同学很nice&#xff01;后期更新发布在这个账号上。。【计算机408备考-数据结构重要知识点-数据结构的定义-哔哩哔哩】https://b23.tv/x7shjNf 数据是信息的载体。数据元素是数据的基本单位。一个数据元素可由若干数据项组成&#xff0c;数据项…

cnpm安装

npm install -g cnpm --registryhttps://registry.npmmirror.com # 注册模块镜像 npm set registry https://registry.npmmirror.com // node-gyp 编译依赖的 node 源码镜像 npm set disturl https://npmmirror.com/dist // 清空缓存 npm cache clean --force // 安装c…

【React】Sigma.js框架网络图-入门篇(2)

通过《【React】Sigma.js框架网络图-入门篇》有了基本认识 由于上一篇直接给出了基本代码示例&#xff0c;可能看着比较复杂也不知道是啥意思&#xff1b; 今天从理论入手重新认识下&#xff01; 一、基本认识 首先&#xff0c;我们先了解下基础术语&#xff1a; 图(Graph)&…