数据结构——顺序表【C】

news2024/9/21 10:41:21

顺序表

  • 1. 顺序表的概念以及结构
    • 1.1概念
    • 1.2静态顺序表和动态顺序表
  • 2. 顺序表接口模拟实现
  • 接口总览
    • 2.1 初始化数据和销毁容器
  • 2.2 顺序表的尾插和尾删
    • 2.3 头插和头删
    • 2.4 任意位置插入和删除数据
    • 2.5 查找数据
  • 3. 顺序表的问题 :

1. 顺序表的概念以及结构

1.1概念

顺序表就是用一段物理地址连续空间储存元素的线性结构,在正常情况下采用数组存储,在数组上完成增删查改等操作。

1.2静态顺序表和动态顺序表

  1. 静态顺序表: 使用长数组存储数据(数组的长度是固定的)
  2. 动态顺序表: 动态开辟数组存储(根据需求来设定数组长度)

2. 顺序表接口模拟实现

接口总览

typedef int SLDatatype;
typedef struct SeqList
{
	SLDatatype* a; //指向动态开辟的数组
	int size;//数组中有效数据的个数
	int capacity;//容器空间大小
}SL;

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

void SLDestory(SL* psl);//顺序表的销毁

void SLPrint(SL* psl);//打印顺序表中的元素

void SLPushBack(SL* psl, SLDatatype num);//尾插

void SLPushFront(SL* psl, SLDatatype num);//头插

void SLPopBack(SL* psl);//尾删

void SLPopFront(SL* psl);//头删

void SLInsert(SL* psl, int pos, SLDatatype num);//从任意位置插入数据

int SLFind(SL* psl, SLDatatype num);//查找顺序表中的元素

void SLErase(SL* psl, int pos);//删除任意位置的元素

2.1 初始化数据和销毁容器

初始化数据:
设置指向数组的指针为空,有效数据个数和容器空间大小设置为0。

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

销毁容器:
所释放动态开辟数组的空间,并设置指向的指针为空指针,有效数据个数和容器空间大小设置为0。

void SLDestory(SL* psl)
{
	assert(psl); //判断psl是否为空

	free(psl->a);
	psl->a = NULL;
	psl->size = psl->capacity = 0;

}

2.2 顺序表的尾插和尾删

在尾插只前我们还要考虑容器是否有足够的空间,若是足够直接插入数据,若是不够则需要动态开辟数组。
注意我们这里默认开辟两倍的空间,在实际中要需要根据需求来开辟容器空间。

void SLCheckCapacity(SL* psl)
{
	assert(psl);
	if (psl->size == psl->capacity)//若是容器中的有效元素等于容器间就要扩容
	{
		int newcapacity = psl->capacity == 0 ? 4 : 2 * psl->capacity;
		SLDatatype* tmp = (SLDatatype*)realloc(psl->a, sizeof(SLDatatype) * newcapacity);
		if (tmp == NULL)
		{
			perror("realloc");
			return;
		}
		psl->a = tmp;
		psl->capacity = newcapacity;
	}
}

尾插:
首先我们要判断容器空间大小,不足则扩容,足够则插入数据。尾插十分容易直接在数组末尾插入数据即可,有效数据加一。
在这里插入图片描述

void SLPushBack(SL* psl, SLDatatype num)
{
	assert(psl);

	SLCheckCapacity(psl);

	psl->a[psl->size++] = num;
}

尾删:
同样的尾删也很容易,只需要将有效数据size-1即可。在这里插入图片描述

void SLPopBack(SL* psl)
{
	assert(psl);
	assert(psl->size > 0);

	psl->size--;
}

2.3 头插和头删

头插:
首先还是容器大小的老问题,不足则扩容,足够则插入数据。头插与尾插不同的是,需要挪动数据将数组中的每一个元素向后移动一位,然后我们在空出的头位置插入数据。
在这里插入图片描述

void SLPushFront(SL* psl, SLDatatype num)
{
	assert(psl);
	 
	SLCheckCapacity(psl);

	int end = psl->size - 1;
	while (end >= 0)
	{
		psl->a[end + 1] = psl->a[end];
		end--;
	}

	psl->a[0] = num;
	psl->size++;
}

头删:
头删也是同样的,让开始位置的后一个数据向前覆盖,将有效数据size-1即可。
在这里插入图片描述

void SLPopFront(SL* psl)
{
	assert(psl);

	int begin = 1;
	while (begin < psl->size)
	{
		psl->a[begin - 1] = psl->a[begin];
		begin++;
	}

	psl->size--;
}

2.4 任意位置插入和删除数据

任意位置插入数据:
这里任意位置的数据就是容器中任意元素下标位置,同样的插入数据还使用挪动数据,将末尾到pos位置的数据向后挪动一位,在空出的pos位置插入数据。

void SLInsert(SL* psl,int pos, SLDatatype num)
{
	assert(psl);

	SLCheckCapacity(psl);

	int end = psl->size;

	while (end >= pos)
	{
		psl->a[end] = psl->a[end - 1];
		end--;
	}

	psl->a[pos] = num;
	psl->size++; 

}

任意位置删除数据:
删除pos位置的数据,还是一样挪动覆盖。

void SLErase(SL* psl,int pos)
{
	assert(psl);

	int end = pos;
	while (end <= psl->size - 1)
	{
		psl->a[end] = psl->a[end + 1];
		end++;
	}
	psl->size--;
}

2.5 查找数据

通过遍历容器中的元素,若是查到则返回元素下标,若是没有找到则返回-1。

int SLFind(SL* psl,SLDatatype num)
{
	assert(psl);
	
	for (int i = 0; i < psl->size; i++)
	{
		if (psl->a[i] == num)
		{
			return i;
		}
	}
	return -1;
}

3. 顺序表的问题 :

  1. 尾部插入的效率还行,头部或者中间插入删除(时间复杂度尾O(N))、需要挪动数据、效率低下。
  2. 满了以后只能扩容。扩容式有一定的消耗的,扩容一般是存在一定的空间浪费。
    (假设空间是100满了,扩容到200,但是只需要插入120个数据,因此有80个空间就浪费掉了,一次扩的越多,可能浪费的越多,一次扩少了,那么有可能就会频繁的扩容)

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

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

相关文章

无缝协作:如何实现VMware与Ubuntu虚拟机的剪切板共享!

文章目录 📖 介绍 📖🏡 演示环境 🏡📒 剪贴板共享 📒📝 VMware设置📝 安装VMware Tools或open-vm-tools📝 验证剪贴板共享功能⚓️ 相关链接 🚓️📖 介绍 📖 无缝的剪贴板共享是提高工作效率的关键。在VMware和Ubuntu虚拟机的协同工作中,能够直接在宿…

【鸿蒙学习笔记】属性学习迭代笔记

这里写目录标题 TextImageColumnRow Text Entry Component struct PracExample {build() {Row() {Text(文本描述).fontSize(40)// 字体大小.fontWeight(FontWeight.Bold)// 加粗.fontColor(Color.Blue)// 字体颜色.backgroundColor(Color.Red)// 背景颜色.width(50%)// 组件宽…

arp缓存中毒实验

文章目录 一、相关知识1.什么是arp&#xff08;地址解析协议&#xff09;2.什么是免费arp&#xff08;1&#xff09;简介&#xff08;2&#xff09;主要应用&#xff08;3&#xff09;代码 3.什么是arp缓存中毒&#xff08;1&#xff09;简介&#xff08;2&#xff09;过程&…

ubuntu使用kubeadm搭建k8s集群

一、卸载k8s kubeadm reset -f modprobe -r ipip lsmod rm -rf ~/.kube/ rm -rf /etc/kubernetes/ rm -rf /etc/systemd/system/kubelet.service.d rm -rf /etc/systemd/system/kubelet.service rm -rf /usr/bin/kube* rm -rf /etc/cni rm -rf /opt/cni rm -rf /var/lib/etcd …

第5章-组合序列类型

#全部是重点知识&#xff0c;必须会。 了解序列和索引|的相关概念 掌握序列的相关操作 掌握列表的相关操作 掌握元组的相关操作 掌握字典的相关操作 掌握集合的相关操作1&#xff0c;序列和索引 1&#xff0c;序列是一个用于存储多个值的连续空间&#xff0c;每一个值都对应一…

python实现建议股票计算器

name 无忧传播 stock_price 19.99 stock_code "003032" stock_rise 1.2 day 7print(f"公司&#xff1a;{name},代码&#xff1a;{stock_code},当前股价&#xff1a;{stock_price}")print("增长系数是&#xff1a;%f&#xff0c;经过%d天后&am…

Git本地仓库的搭建与使用

目录 一、前言 二、Linux下搭建 git 仓库 三、Windows下搭建 git 仓库 一、前言 做项目时&#xff0c;我们常常需要将自己的代码进行托管&#xff0c;但有时候 Github 的速度属实叫人流泪。有的人会选择 Gitee 等进行托管代码&#xff0c;这当然是可以的。那如果没有其他代码…

【VUE基础】VUE3第一节—vite创建vue3工程

什么是VUE Vue (发音为 /vjuː/&#xff0c;类似 view) 是一款用于构建用户界面的 JavaScript 框架。它基于标准 HTML、CSS 和 JavaScript 构建&#xff0c;并提供了一套声明式的、组件化的编程模型&#xff0c;帮助你高效地开发用户界面。无论是简单还是复杂的界面&#xff0…

藏汉翻译通作为翻译软件的优势有哪些?

藏汉翻译通作为一款专业的藏汉双语翻译软件&#xff0c;具有以下优势&#xff1a; 人工智能技术应用&#xff1a;藏汉翻译通利用了人工智能翻译和语音识别合成技术&#xff0c;提供智能藏文翻译服务。 高准确率&#xff1a;文字识别准确率可达90%&#xff0c;语音识别转化文字…

IDEA新建项目并撰写Java代码的方法

本文介绍在IntelliJ IDEA软件中&#xff0c;新建项目或打开已有项目&#xff0c;并撰写Java代码的具体方法&#xff1b;Groovy等语言的代码也可以基于这种方法来撰写。 在之前的文章IntelliJ IDEA社区版在Windows电脑中的下载、安装方法&#xff08;https://blog.csdn.net/zheb…

Echarts水球图(liquidFill)添加文字

效果 代码 {type: liquidFill,shape: shapes[0].value,radius: 90%,data: [{name: 独立百货,value: 0}],center: [50%, 50%],color: [{type: linear,x: 0,y: 0,x2: 0,y2: 1,colorStops: [{offset: 0,color: #446bf5},{offset: 1,color: #2ca3e2}],globalCoord: false}],backgro…

混合贪心算法求解地铁线路调度

一、问题描述 城市轨道交通的繁荣发展&#xff0c;带来了车辆资源需求的日益增加。如何兼顾运营服务水平和运营成本&#xff0c;以最少的车底优质地完成运输任务成为一大严峻问题。本题在后续的描述中将由多辆动车和拖车组合而成的车组称为车底。在日常的运营组织中&#xff0…

算力狂飙|WAIC 2024上的服务器

7月7日&#xff0c;2024世界人工智能大会暨人工智能全球治理高级别会议&#xff08;WAIC 2024&#xff09;在上海落下帷幕。这场备受瞩目的AI盛宴与热辣夏日碰撞&#xff0c;吸引了全球科技、产业及学术界的广泛关注&#xff0c;线下参观人数突破30万人次&#xff0c;线上流量突…

DOM(文档对象模型)生命周期事件

前言 DOM 生命周期事件涉及到从创建、更新到销毁 DOM 元素的不同阶段。 ● 我们来看下当HTML文档加载完再执行JavaScript代码 document.addEventListener(DOMContentLoaded, function (e) {console.log(HTML parsed adn DOM tree built!, e); })● 除此之外&#xff0c;浏览…

Linux | 安装lb-toolkits 1.2.4库

Linux | 安装 lb-toolkits 最近又需要下载葵花的数据&#xff0c;之前分享过一次代码。今天发现之前的环境不小心被我删了&#xff0c;而运行相关的代码需要安装lb-toolkits这个库&#xff0c;今天正好记录了一下安装lb-toolkits的过程。 这里安装的版本是1.2.4&#xff0c;别…

【前端从入门到精通:第十二课: JS运算符及分支结构】

JavaScript运算符 算数运算符 关于自增自减运算 自增或者自减运算就是在本身的基础上进行1或者-1的操作 自增或者自减运算符可以在变量前也可以在变量后&#xff0c;但是意义不同 自增自减运算符如果在变量前&#xff0c;是先进行自增或者自减运算&#xff0c;在将变量给别人用…

基于springboot+vue实现的厨艺交流平台(文末源码+Lw)093

93基于SpringBootVue的实现的厨艺交流平台&#xff08;源码数据库万字Lun文流程图ER图结构图演示视频软件包&#xff09; 系统功能&#xff1a; 这次开发的厨艺交流平台功能有个人中心&#xff0c;食材分类管理&#xff0c;用户管理&#xff0c;菜品分类管理&#xff0c;菜谱信…

力扣第一题

1. 两数之和 提示 给定一个整数数组 nums 和一个整数目标值 target&#xff0c;请你在该数组中找出 和为目标值 target 的那 两个 整数&#xff0c;并返回它们的数组下标。 你可以假设每种输入只会对应一个答案。但是&#xff0c;数组中同一个元素在答案里不能重复出现。 你可…

CSS技巧专栏:一日一例 2.纯CSS实现 多彩边框按钮特效

大家好,今天是 CSS技巧一日一例 专栏的第二篇《纯CSS实现多彩边框按钮特效》 先看图: 开工前的准备工作 正如昨日所讲,为了案例的表现,也处于书写的习惯,在今天的案例开工前,先把昨天的准备工作重做一遍。 清除浏览器的默认样式定义页面基本颜色设定body的样式清除butt…

深入理解 Qt 的 `moveToThread`:提升多线程应用性能的关键

&#x1f60e; 作者介绍&#xff1a;欢迎来到我的主页&#x1f448;&#xff0c;我是程序员行者孙&#xff0c;一个热爱分享技术的制能工人。计算机本硕&#xff0c;人工制能研究生。公众号&#xff1a;AI Sun&#xff08;领取大厂面经等资料&#xff09;&#xff0c;欢迎加我的…