顺序表(C语言详细版)

1. 线性表

线性表(lina list)是n个具有相同特性的数据元素的有限序列。线性表是一种在实际中广泛使用的数据结构,常见的线性表:顺序表、链表、栈、队列、字符串......

线性表在逻辑上是线性结构,也就是说连续的一条直线。但是在物理结构上并不一定是连续的,线性表在物理上存储时,通常以数组和链式结构的形式存储。

2. 顺序表实现

2.1 概念及结构

顺序表是用一段物理地址连续的存储单元依次存储数据元素的线性结构,一般情况下采用数组存储。在数组上完成数据的增删查改。

顺序表一般可以分为:

1.静态顺序表:使用定长数组存储。

2.动态顺序表:使用动态开辟的数组存储。

#define N 100
// 静态顺序表
struct SeqList
{int arr[N];int size;	// 有效数据个数
};

typedef int SLDataType;// 动态顺序表
typedef struct SeqList
{SLDataType* arr;SLDataType size;	// 有效数据个数SLDataType capacity;	// 空间大小
}SL;

注意:静态顺序表只适用于确定知道需要多少数据的场景。静态顺序表的定长数组导致N定大了,空间开多了浪费,开少了不够用。所以现实中基本都是使用动态顺序表,根据需要动态地分配空间大小,所以下面我们实现动态顺序表。

2.2 顺序表初始化

// 顺序表初始化
void SLInit(SL* ps);

首先,我们需要初始化数组,数组首元素地址 ps->arr 置为NULL;有效数字个数 size 和空间容量capacity 大小都置为0。

// 顺序表初始化
void SLInit(SL* ps)
{ps->arr = NULL;ps->size = ps->capacity = 0;
}

2.3 顺序表销毁

// 顺序表销毁
void SLDestroy(SL* ps);

我们使用完顺序表之后,都需要把顺序表进行销毁,以免造成内存被占用和内存泄漏问题。

首先,需要把开辟的空间 free 掉,再将数组首元素地址 ps->arr 置为NULL;有效数字个数 size 和空间容量 capacity 大小都置为0。

// 顺序表销毁
void SLDestroy(SL* ps)
{if (ps->arr){free(ps->arr);}ps->arr = NULL;ps->size = ps->capacity = 0;
}

2.4 顺序表打印

// 顺序表打印
void SLPrint(SL s);

为了更好地对程序进行调试,我们这里需要写一个打印程序,以便我们测试每一个接口函数。

// 顺序表打印
void SLPrint(SL s)
{for (int i = 0; i < s.size; i++){printf("%d ", s.arr[i]);}printf("\n");
}

附:我们完成这些前导工作,接下来我们就可以正式编写顺序表的功能函数。

2.5 顺序表尾插

// 顺序表尾插
void SLPushBack(SL* ps, SLDataType x);

我们得分两种情况:

不过在尾插元素之前,我们必须得确保数组空间大小是足够的,也就是说得有空间插入元素。如果说空间容量不够的话,我们就得扩容,所以说在尾插之前,我们得判断空间大小是否足够,不够咱就扩容。我们这里得写一个内存容量检查函数。

这里我们还得注意一个点:就是我们内存空间不够的情况下,一般我们是以2倍或者3倍  capacity(容量) * 2 * sizeof(数据类型) 去开辟空间。

// 检查内存函数
void SLCheckCapacity(SL* ps)
{// 插入数据之前看空间够不够if (ps->capacity == ps->size){// 申请空间// 申请之前,要判断一下capacity是否为0int newCapacity = ps->capacity == 0 ? 4 : 2 * ps->capacity;错误写法:这里不要直接这样写,要不然申请空间失败的话,前面的数据会丢失//ps->arr = (SLDataType*)realloc(ps->arr, newCapacity * 2 * sizeof(SLDataType));// 正确写法SLDataType* tmp = (SLDataType*)realloc(ps->arr, newCapacity * 2 * sizeof(SLDataType));// 如果申请失败if (tmp == NULL){perror("realloc fail!");exit(1);	// 直接退出程序,不再继续执行}// 空间申请成功ps->arr = tmp;ps->capacity = newCapacity;}
}

检查开辟完空间后,我们就可以进行下一步,顺序表尾插接口函数编写。

步骤:

① 程序开始前,我们要断言一下,确保指针是有效的,不是NULL;

② 检查内存是否足够;

③ 将我们需要的 x 尾插入下标 ps->size 的位置,插完之后,数组元素总个数 ps->size 得加1。

// 顺序表尾插
void SLPushBack(SL* ps, SLDataType x)
{温柔的解决方式//if (ps == NULL)//	return;assert(ps); // 等价于assert(ps != NULL)// 检查内存SLCheckCapacity(ps);/*ps->arr[ps->size] = x;++ps->size;*/ps->arr[ps->size++] = x;
}

2.6 顺序表头插

// 顺序表头插
void SLPushFront(SL* ps, SLDataType x);

我们也得分两种情况:

不过我们在头插元素之前,我们也得确保数组空间大小是足够的,所以我们头插之前也得调用一下内存检查函数 SLCheckCapacity,保证我们内存容量是足够的。

步骤:

① 程序开始前,我们要断言一下,确保指针是有效的,不是NULL;

② 检查内存是否足够;

③ 将我们需要的 x 头插入下标 0 的位置,插完之后,数组元素总个数 ps->size 得加1。

// 顺序表头插
void SLPushFront(SL* ps, SLDataType x)
{assert(ps);// 检查内存SLCheckCapacity(ps);// 先让顺序表中已有的数据整体往后挪动一位for (int i = ps->size; i > 0; i--){ps->arr[i] = ps->arr[i - 1]; // arr[1] = arr[0]}ps->arr[0] = x;ps->size++;
}

2.6 顺序表尾删

// 顺序表尾删
void SLPopBack(SL* ps);

我们删除数据不是说要把这个数据从数组中去除,而是说我们这个所谓的“删除的数据”不能被访问,所以我们只需把数组中有效的元素个数 size - 1 即可,并不需要把这个数据变成什么其他的数,这是非常多余的(如果非要更改删除数据也不是不可)。

步骤:

① 程序开始前,我们要断言一下,确保指针是有效的,不是NULL;

② 断言一下,数据有效个数不能为0;

③ 将数据有效个数 size - 1。

// 顺序表尾删
void SLPopBack(SL* ps)
{assert(ps);assert(ps->size);	// 顺序表有效数字不能为0// 顺序表不能为空//ps->arr[ps->size - 1] = -1;	// 这行代码有点多余ps->size--;
}

附:尾删还是非常简单的!

2.7 顺序表

// 顺序表头删
void SLPopFront(SL* ps);

头删数据之后,我们还需要每个数据往前一位,最后 size - 1。

步骤:

① 程序开始前,我们要断言一下,确保指针是有效的,不是NULL;

② 断言一下,数据有效个数不能为0;

③  然后将每个数据往前移动一位;

③ 将数据有效个数 size - 1。

// 顺序表头删
void SLPopFront(SL* ps)
{assert(ps);assert(ps->size);	// 顺序表有效数字不能为0// 数据整体往前挪动一位for (int i = 0; i < ps->size - 1; i++){ps->arr[i] = ps->arr[i + 1]; // 最后一次,arr[size - 2] = arr[size - 1]}ps->size--;
}

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

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

相关文章

一文汇总全球热门新闻API

新闻API通过提供快速、准确和全面的新闻内容&#xff0c;已经成为现代社会不可或缺的一部分&#xff0c;对人们的生活、工作环境和科技发展产生了深远的影响。新闻API使人们能够快速获取来自世界各地的实时新闻和信息&#xff0c;提高了信息的可访问性。通过新闻API&#xff0c…

C++算法学习心得八.动态规划算法(6)

1.最长递增子序列&#xff08;300题&#xff09; 题目描述&#xff1a; 给你一个整数数组 nums &#xff0c;找到其中最长严格递增子序列的长度。 子序列是由数组派生而来的序列&#xff0c;删除&#xff08;或不删除&#xff09;数组中的元素而不改变其余元素的顺序。例如&…

Redis分布式集群部署

目录 一. 原理简述 二. 集群配置​​​​​​​ 2.1 环境准备 2.2 编译安装一个redis 2.3 创建集群 2.4 写入数据测试 实验一&#xff1a; 实验二&#xff1a; 实验三&#xff1a; 实验四&#xff1a; 添加节点 自动分配槽位 提升节点为master&#xff1a; 实验…

关于电商平台分类||电商平台商品分类接口|电商平台商品数据

电商平台 做电商&#xff0c;则要有电商平台&#xff0c;一个为 企业 或 个人 提供网上交易洽谈的平台。. 企业电子商务平台是建立在 Internet 网上进行商务活动的虚拟网络空间和保障商务顺利运营的管理环境&#xff1b;是协调、整合 信息流 、货物流、 资金流 有序、关联、高效…

会员信息一键同步!微盟与客如云联手打造智能服务新体验!

客户介绍 某房地产开发有限公司&#xff0c;自成立以来一直深耕于房地产行业&#xff0c;凭借卓越的开发实力和前瞻性的市场眼光&#xff0c;成为了业界备受瞩目的企业。多年来&#xff0c;该公司始终坚持“品质至上&#xff0c;客户为先”的经营理念&#xff0c;致力于为客户…

新一代Java框架Quarkus的性能优化与应用

新一代Java框架Quarkus的性能优化与应用 大家好&#xff0c;我是免费搭建查券返利机器人省钱赚佣金就用微赚淘客系统3.0的小编&#xff0c;也是冬天不穿秋裤&#xff0c;天冷也要风度的程序猿&#xff01; 引言 随着云原生技术的发展&#xff0c;Java开发者们对于构建轻量级、…

JavaScript 编程语言【 数据类型】过滤|排序|映射|迭代

文章目录 将 border-left-width 转换成 borderLeftWidth过滤范围原位&#xff08;in place&#xff09;过滤范围降序排列复制和排序数组创建一个可扩展的 calculator映射到 names映射到对象按年龄对用户排序随机排列数组获取平均年龄数组去重从数组创建键&#xff08;值&#x…

掌握React与TypeScript:从零开始绘制中国地图

最近我需要使用reactts绘制一个界面&#xff0c;里面需要以中国地图的形式展示区块链从2019-2024年这五年的备案以及注销情况&#xff0c;所以研究了一下这方面的工作&#xff0c;初步有了一些成果&#xff0c;所以现在做一些分享&#xff0c;希望对大家有帮助&#xff01; 在这…

手把手搞定报名亚马逊科技认证

引言 亚马逊云科技认证考试为我们这些技术从业者提供了提升专业技能的机会。无论选择线上还是线下考试&#xff0c;每种方式都有其独特的优势和挑战。选择合适的考试方式将帮助我们更好地展示自己的技术水平。以下是我对不同考试方式的优缺点介绍&#xff0c;以及各科目的考试…

【pytorch12】什么是梯度

说明 导数偏微分梯度 梯度&#xff1a;是一个向量&#xff0c;向量的每一个轴是每一个方向上的偏微分 梯度是有方向也有大小&#xff0c;梯度的方向代表函数在当前点的一个增长的方向&#xff0c;然后这个向量的长度代表了这个点增长的速率 蓝色代表比较小的值&#xff0c;红色…

七月论文审稿GPT第5版:拿我司七月的早期paper-7方面review数据集微调LLama 3

前言 llama 3出来后&#xff0c;为了通过paper-review的数据集微调3&#xff0c;有以下各种方式 不用任何框架 工具 技术&#xff0c;直接微调原生的llama 3&#xff0c;毕竟也有8k长度了 效果不期望有多高&#xff0c;纯作为baseline通过PI&#xff0c;把llama 3的8K长度扩展…

基于Linux的云端垃圾分类助手

项目简介 本项目旨在开发一个基于嵌入式系统的智能垃圾分类装置。该装置能够通过串口通信、语音播报、网络通信等多种方式&#xff0c;实现垃圾的自动识别和分类投放。系统采用多线程设计&#xff0c;确保各功能模块高效并行工作。 项目功能 垃圾分类识别 系统使用摄像头拍摄…

解密tar文件解压的Java实现技术

解密tar文件解压的Java实现技术 大家好&#xff0c;我是免费搭建查券返利机器人省钱赚佣金就用微赚淘客系统3.0的小编&#xff0c;也是冬天不穿秋裤&#xff0c;天冷也要风度的程序猿&#xff01; 引言 在日常的软件开发和系统管理中&#xff0c;经常会遇到需要解压缩文件的…

代码随想三刷动态规划篇5

代码随想三刷动态规划篇5 377. 组合总和 Ⅳ题目代码 57. 爬楼梯&#xff08;第八期模拟笔试&#xff09;题目代码 322. 零钱兑换题目代码 279. 完全平方数题目代码 377. 组合总和 Ⅳ 题目 链接 代码 class Solution {public int combinationSum4(int[] nums, int target) {…

SM2的签名值byte数组与ASN.1互转

ASN.1抽象语言标记(Abstract Syntax Notation One) ASN.1是一种 ISO/ITU-T 标准,描述了一种对数据进行表示、编码、传输和解码的数据格式,它提供了一整套正规的格式用于描述对象的结构。 一、该结构的应用场景 例如在做待签名的数字信封时,数字信封使用ASN.1封装,这个时…

MySQL-行级锁(行锁、间隙锁、临键锁)

文章目录 1、介绍2、查看意向锁及行锁的加锁情况3、行锁的演示3.1、普通的select语句&#xff0c;执行时&#xff0c;不会加锁3.2、select * from stu where id 1 lock in share mode;3.3、共享锁与共享锁之间兼容。3.4、共享锁与排他锁之间互斥。3.5、排它锁与排他锁之间互斥3…

论文调研_Awesome-Binary-Similarity

0. 概述 对 Awesome-Binary-Similarity 中列出的论文进行调研,重点总结这些论文的研究动机与未来研究方向。 1. 调研内容 论文名称发表时间发表期刊期刊等级研究单位BinaryAI: Binary Software Composition Analysis via Intelligent Binary Source Code Matching2024年ICSE…

每日一题---OJ题:分隔链表

片头 嗨&#xff01;小伙伴们&#xff0c;大家好&#xff01;今天我们一起来看看这道题----分隔链表 emmmm&#xff0c;这道题&#xff0c;看描述应该不算太难&#xff0c;我们一起来画一画图呗&#xff01; 题目读懂了&#xff0c;那么如何破解这道题呢&#xff1f; 思路&…

microApp vue3+vite+ts 子应用接入改造

公司做了一个平台,使用的是microApp,需要把现有的一些系统作为子系统改造一下接入这个平台,所以下面我说的都是子应用的改造,vue2的改造比较简单,主要的vue3+vite+ts的改造。 参考官网 1、设置跨应用支持 vite默认开启跨域支持,不需要额外配置。 2、注册卸载函数 // …

nand flash spec

nand flash简介 nand flash是一种非易失性存储器。它具有高存储密度、低成本和高耐用性的特点。 nand flash的特性是非易失性&#xff0c;即在电源关闭的情况下&#xff0c;数据仍然保留。 nand flash的存储单元由浮动栅极晶体管组成&#xff0c;每个存储单元可以存储一位或多…