数据结构:顺序表(动态顺序表)

news2024/11/24 3:46:08

专栏说明:本专栏用于数据结构复习,文章中出现的代码由C语言实现,在专栏中会涉及到部分OJ题目,如对你学习有所帮助,可以点赞鼓励一下博主喔💓


  • 博客主页:Duck Bro 博客主页
  • 系列专栏:数据结构专栏
  • 关注博主,后期持续更新系列文章
  • 如果有错误感谢请大家批评指出,及时修改
  • 感谢大家点赞👍收藏⭐评论✍

数据结构:顺序表(动态顺序表)

目录

  • 数据结构:顺序表(动态顺序表)
    • 1. 概念与结构
      • 1.1 概念
      • 1.2 结构
    • 2. 接口实现
      • 2.1 动态顺序表结构
      • 2.2 顺序表初始化
      • 2.3 顺序表销毁
      • 2.4 检查空间、扩容
      • 2.5 顺序表尾插
      • 2.6 顺序表尾删
      • 2.7 顺序表头插
      • 2.8 顺序表头删
      • 2.9 顺序表查找
      • 2.10 在pos位置插入x
      • 2.11 删除pos位置值
      • 2.12 修改pos位置值
      • 2.13 打印顺序表
    • 3. 详细代码页
      • 3.1 SeqList.h
      • 3.2 SeqList.c
      • 3.3 main.c


1. 概念与结构

1.1 概念

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

1.2 结构

静态顺序表:使用定长数组存储元素。
在这里插入图片描述

#define N 7
typedef int DataType;
typedef struct SeqList
{
	DataType a[N];
	int size;
	int capacity;
}SL;

动态顺序表:使用动态开辟的数组存储。
在这里插入图片描述

typedef int DataType;
typedef struct SeqList
{
	DataType* a;
	int size;
	int capacity;
}SL;

2. 接口实现

2.1 动态顺序表结构

//顺序表动态存储
typedef int DataType;
typedef struct SeqList
{
	DataType* a;	//指点动态开辟数组
	int size;		//有效数据个数
	int capacity;	//容量空间大小
}SL;

2.2 顺序表初始化

void SLInit(SL* pc)
{
	//断言
	assert(pc);
	//pc->a = NULL;
	pc->a = (DataType*)malloc(sizeof(DataType) * 4);
	//判断是否为空
	if (pc->a == NULL)
	{
		//报错提示
		perror("SLInit faild");
		//退出程序
		exit(-1);
	}
	//顺序表内的数据个数
	pc->size = 0;
	//顺序表内的容量
	pc->capacity = 4;
}

2.3 顺序表销毁

void SLDestroy(SL* pc)
{
	//断言
	assert(pc);
	//释放内存
	free(pc->a);
	//将指针置为空
	pc->a = NULL;
	//设置数据个数和容量为0个
	pc->size = 0;
	pc->capacity = 0;
}

2.4 检查空间、扩容

void SLCheckCapacity(SL* pc)
{
	//断言
	assert(pc);
	//如果size==capacity,则进行二倍扩容
	if (pc->size == pc->capacity)
	{
		DataType* temp = (DataType*)realloc(pc->a, pc->capacity * sizeof(DataType) * 2);
		//进行判断是否开辟成功
		if (temp == NULL)
		{
			perror("SLCheckCapacity faild");
			exit(-1);
		}
		pc->a = temp;
		pc->capacity *= 2;
	}
}

2.5 顺序表尾插

void SLPushBack(SL* pc, DataType x)
{
	assert(pc);

	/*assert(pc);
	SLCheckCapacity(pc);
	pc->a[pc->size] = x;
	pc->size++;*/
	SLInsert(pc, pc->size, x);
}

2.6 顺序表尾删

void SLPopBack(SL* pc)
{
	assert(pc);
	/*assert(pc);
	assert(pc->size);
	pc->size--;*/
	SLErase(pc, pc->size - 1);
}

2.7 顺序表头插

void SLPushFront(SL* pc, DataType x)
{
	assert(pc);

	断言
	//assert(pc);
	检查空间是否足够
	//SLCheckCapacity(pc);
	end为顺序表中最后一个数据的下标
	//int end = pc->size - 1;
	将所有数据进行后移
	//while (end >= 0)
	//{
	//	pc->a[end + 1] = pc->a[end];
	//	--end;

	//}
	//pc->a[0] = x;
	//pc->size++;
	SLInsert(pc, 0, x);

}

2.8 顺序表头删

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

	/*assert(pc->size > 0);
	int begin = 1;
	while (begin < pc->size)
	{
		pc->a[begin - 1] = pc->a[begin];
		begin++;

	}
	pc->size--;*/
	SLErase(pc, 0);
}

2.9 顺序表查找

int SLFind(SL* pc, DataType x)
{

	assert(pc);
	for (int i = 0; i < pc->size; i++)
	{
		if (x == pc->a[i])
		{
			return i;
		}
	}
	return -1;
}

2.10 在pos位置插入x

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

2.11 删除pos位置值

void SLErase(SL* pc, int pos)
{
	assert(pc);
	assert(pos>=0&&pos<pc->size);

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

2.12 修改pos位置值

void SLModify(SL* pc, int pos, DataType x)
{
	assert(pc);

	assert(pos <= 0 && pos < pc->size);
	pc->a[pos] = x;

}

2.13 打印顺序表

void SLPrintf(SL* pc)
{
	//断言
	assert(pc);
	//遍历
	int i = 0;
	for (i = 0; i < pc->size; i++)
	{
		printf("%d ", pc->a[i]);
	}
	printf("\n");
}

3. 详细代码页

3.1 SeqList.h

#define  _CRT_SECURE_NO_WARNINGS 1
#pragma once
#include<stdio.h>
#include<assert.h>
#include<stdlib.h>
typedef int DataType;
typedef struct SeqList
{
	DataType* a;
	int size;
	int capacity;
}SL;

//顺序表初始化
void SLInit(SL* pc);
//顺序表销毁
void SLDestroy(SL* pc);
//容量检查,并进行扩容
void SLCheckCapacity(SL* pc);
//打印顺序表中的数据 遍历顺序表
void SLPrintf(SL* pc);

//顺序表头插
void SLPushFront(SL* pc, DataType x);
//顺序表尾删
void SLPopBack(SL* pc);
//顺序表尾插
void SLPushBack(SL* pc, DataType x);
//顺序表头删
void SLPopFront(SL* pc);

//查找位置
int SLFind(SL* pc ,DataType x);
//顺序表pos位置前插入X
void SLInsert(SL* pc, int pos,DataType x);
//顺序表删除pos位置值
void SLErase(SL* pc,int pos);
//修改pos位置值
void SLModify(SL* pc, int pos,DataType x);

3.2 SeqList.c

#define  _CRT_SECURE_NO_WARNINGS 1
#include"SeqList.h"


void SLInit(SL* pc)
{
	//断言
	assert(pc);
	//pc->a = NULL;
	pc->a = (DataType*)malloc(sizeof(DataType) * 4);
	//判断是否为空
	if (pc->a == NULL)
	{
		//报错提示
		perror("SLInit faild");
		//退出程序
		exit(-1);
	}
	//顺序表内的数据个数
	pc->size = 0;
	//顺序表内的容量
	pc->capacity = 4;
}

void SLDestroy(SL* pc)
{
	//断言
	assert(pc);
	//释放内存
	free(pc->a);
	//将指针置为空
	pc->a = NULL;
	//设置数据个数和容量为0个
	pc->size = 0;
	pc->capacity = 0;

}

void SLCheckCapacity(SL* pc)
{
	//断言
	assert(pc);
	//如果size==capacity,则进行二倍扩容
	if (pc->size == pc->capacity)
	{
		DataType* temp = (DataType*)realloc(pc->a, pc->capacity * sizeof(DataType) * 2);
		//进行判断是否开辟成功
		if (temp == NULL)
		{
			perror("SLCheckCapacity faild");
			exit(-1);
		}
		pc->a = temp;
		pc->capacity *= 2;

	}
}

void SLPrintf(SL* pc)
{
	//断言
	assert(pc);
	//遍历
	int i = 0;
	for (i = 0; i < pc->size; i++)
	{
		printf("%d ", pc->a[i]);
	}
	printf("\n");
}

void SLPushFront(SL* pc, DataType x)
{
	assert(pc);

	断言
	//assert(pc);
	检查空间是否足够
	//SLCheckCapacity(pc);
	end为顺序表中最后一个数据的下标
	//int end = pc->size - 1;
	将所有数据进行后移
	//while (end >= 0)
	//{
	//	pc->a[end + 1] = pc->a[end];
	//	--end;

	//}
	//pc->a[0] = x;
	//pc->size++;
	SLInsert(pc, 0, x);

}

void SLPopBack(SL* pc)
{
	assert(pc);
	/*assert(pc);
	assert(pc->size);
	pc->size--;*/
	SLErase(pc, pc->size - 1);
}

void SLPushBack(SL* pc, DataType x)
{
	assert(pc);

	/*assert(pc);
	SLCheckCapacity(pc);
	pc->a[pc->size] = x;
	pc->size++;*/
	SLInsert(pc, pc->size, x);
}

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

	/*assert(pc->size > 0);
	int begin = 1;
	while (begin < pc->size)
	{
		pc->a[begin - 1] = pc->a[begin];
		begin++;

	}
	pc->size--;*/
	SLErase(pc, 0);
}

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

void SLErase(SL* pc, int pos)
{
	assert(pc);
	assert(pos>=0&&pos<pc->size);

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

int SLFind(SL* pc, DataType x)
{

	assert(pc);
	for (int i = 0; i < pc->size; i++)
	{
		if (x == pc->a[i])
		{
			return i;
		}
	}
	return -1;
}

void SLModify(SL* pc, int pos, DataType x)
{
	assert(pc);

	assert(pos <= 0 && pos < pc->size);
	pc->a[pos] = x;

}

3.3 main.c


#include "SeqList.h"
void test1()
{
	//测试创建顺序表初始化 销毁
	SL s;
	SLInit(&s);
	SLDestroy(&s);
}

void test2()
{
	//测试顺序表尾插插
	SL s1;
	SLInit(&s1);
	
	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	//SLPushFront(&s1, 4);
	//SLPushFront(&s1, 4);

	//SLPopBack(&s1);
	//SLPopBack(&s1);
	SLPopBack(&s1);
	SLPopBack(&s1);


	SLPushBack(&s1, 67);
	SLPushBack(&s1, 67);
	SLPushBack(&s1, 67);

	SLPrintf(&s1);
	SLDestroy(&s1);
}

void test3()
{
	//测试顺序表尾插插
	SL s1;
	SLInit(&s1);

	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	SLPrintf(&s1);

	//SLPushFront(&s1, 4);
	SLPushFront(&s1, 66);



	SLPrintf(&s1);
	SLDestroy(&s1);
}

void test4()
{
	//测试顺序表尾插插
	SL s1;
	SLInit(&s1);

	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	SLPushBack(&s1, 5);
	//SLInsert(&s1, 2, 7);
	int x = 0;
	scanf("%d", &x);
	int pos = SLFind(&s1, x);
	if (pos != -1)
	{
		SLInsert(&s1, pos, 50);
	}


	SLPrintf(&s1);
	SLDestroy(&s1);
}
void test5()
{
	//测试顺序表尾插插
	SL s1;
	SLInit(&s1);

	SLPushBack(&s1, 1);
	SLPushBack(&s1, 2);
	SLPushBack(&s1, 3);
	SLPushBack(&s1, 4);
	SLPushBack(&s1, 5);
	//SLInsert(&s1, 2, 7);
	SLPopBack(&s1);
	SLPopFront(&s1);


	SLPrintf(&s1);
	SLDestroy(&s1);
}
int main()
{
	//test1();
	//test2();
	//test3();
	//test4();
	test5();

	return 0;
}

在这里插入图片描述

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

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

相关文章

力扣动态规划基础版(矩阵型)

62.不同路径&#xff08;唯一路径问题&#xff09; 62. 不同路径https://leetcode.cn/problems/unique-paths/ 方法一&#xff1a;动态规划 找状态转移方程&#xff0c;也就是说它从左上角走到右下角&#xff0c;只能往右或者往下走&#xff0c;那么设置一个位置为&#xff…

音视频入门基础:FLV专题(23)——FFmpeg源码中,获取FLV文件音频信息的实现(下)

音视频入门基础&#xff1a;FLV专题系列文章&#xff1a; 音视频入门基础&#xff1a;FLV专题&#xff08;1&#xff09;——FLV官方文档下载 音视频入门基础&#xff1a;FLV专题&#xff08;2&#xff09;——使用FFmpeg命令生成flv文件 音视频入门基础&#xff1a;FLV专题…

A021基于Spring Boot的自习室管理和预约系统设计与实现

&#x1f64a;作者简介&#xff1a;在校研究生&#xff0c;拥有计算机专业的研究生开发团队&#xff0c;分享技术代码帮助学生学习&#xff0c;独立完成自己的网站项目。 代码可以查看文章末尾⬇️联系方式获取&#xff0c;记得注明来意哦~&#x1f339; 赠送计算机毕业设计600…

qt QShortcut详解

1、概述 QShortcut是Qt框架中的一个类&#xff0c;它提供了一种创建键盘快捷键的方式。通过QShortcut&#xff0c;开发者可以将特定的键盘组合&#xff08;如CtrlC、AltF4等&#xff09;与应用程序中的动作&#xff08;如复制、关闭窗口等&#xff09;关联起来。当用户在应用程…

注意力机制的目的:理解语义;编码器嵌入高纬空间计算;注意力得分“得到S*V”;解码器掩码和交叉注意力层用于训练;最终的编码器和输出实现大模型

目录 注意力机制的目的:理解语义中的它是小白兔 词编码器嵌入高纬空间 计算注意力得分“得到S*V” 权重QKV:连接权重 训练阶段使用解码器:翻译后的语句 解码器掩码和交叉注意力层用于训练 最终的编码器和输出实现大模型 Transformer模型中,QKV QKV的作用 举例说明…

jmeter常用配置元件介绍总结之取样器

系列文章目录 1.windows、linux安装jmeter及设置中文显示 2.jmeter常用配置元件介绍总结之安装插件 3.jmeter常用配置元件介绍总结之取样器 jmeter常用配置元件介绍总结之取样器 2.取样器2.1.HTTP请求2.2.Debug Sampler2.3.JSR223 Sampler2.4.JDBC Connection Configuration和J…

【大数据学习 | kafka】简述kafka的消费者consumer

1. 消费者的结构 能够在kafka中拉取数据进行消费的组件或者程序都叫做消费者。 这里面要涉及到一个动作叫做拉取。 首先我们要知道kafka这个消息队列主要的功能就是起到缓冲的作用&#xff0c;比如flume采集数据然后交给spark或者flink进行计算分析&#xff0c;但是flume采用的…

从零开始训练一个大语言模型需要多少天?

一&#xff0c;前言 在AI领域&#xff0c;训练一个大型语言模型&#xff08;LLM&#xff09;是一个耗时且复杂的过程。几乎每个做大型语言模型&#xff08;LLM&#xff09;训练的人都会被问到&#xff1a;“从零开始&#xff0c;训练大语言模型需要多久和花多少钱&#xff1f;”…

【SQL50】day 1

目录 1.可回收且低脂的产品 2.寻找用户推荐人 3.使用唯一标识码替换员工ID 4.产品销售分析 I 5.有趣的电影 6.平均售价 7.每位教师所教授的科目种类的数量 8.平均售价 1.可回收且低脂的产品 # Write your MySQL query statement below select product_id from Products w…

Qt菜单功能实现

本文介绍Qt菜单功能实现。 Qt开发过程中&#xff0c;菜单功能用的还是比较多的&#xff0c;本文针对菜单栏和右键菜单功能实现作简要描述。 1.菜单栏 1)界面设计 在界面中添加菜单栏&#xff08;本例中名为“menubar”&#xff09;&#xff0c;并依次添加需要的菜单&#x…

Jupyter Notebook添加kernel的解决方案

大家好,我是爱编程的喵喵。双985硕士毕业,现担任全栈工程师一职,热衷于将数据思维应用到工作与生活中。从事机器学习以及相关的前后端开发工作。曾在阿里云、科大讯飞、CCF等比赛获得多次Top名次。现为CSDN博客专家、人工智能领域优质创作者。喜欢通过博客创作的方式对所学的…

Java:二维数组

目录 1. 二维数组的基础格式 1.1 二维数组变量的创建 —— 3种形式 1.2 二维数组的初始化 \1 动态初始化 \2 静态初始化 2. 二维数组的大小 和 内存分配 3. 二维数组的不规则初始化 4. 遍历二维数组 4.1 for循环 ​编辑 4.2 for-each循环 5. 二维数组 与 方法 5.1…

手机内卷下一站,AI Agent

作者 | 辰纹 来源 | 洞见新研社 2024年除夕夜&#xff0c;OPPO在央视春晚即将开始前举办了一场“史上最短发布会”&#xff0c;OPPO首席产品官刘作虎宣布&#xff0c;“OPPO正式进入AI手机时代”。 春节假期刚过&#xff0c;魅族又公开表示&#xff0c;将停止“传统智能手机…

Python实战:调用淘宝API以抓取商品页面数据

在数据驱动的商业决策中&#xff0c;获取电商平台的商品数据至关重要。淘宝作为中国最大的在线购物平台&#xff0c;其商品数据对于市场分析、价格监控和竞品研究等方面都具有极高的价值。本文将通过一个Python实战案例&#xff0c;展示如何调用淘宝API来抓取商品页面的数据。 …

SpringBoot14-任务

任务 14.1异步任务 所谓异步&#xff0c;在某些功能实现时可能要花费一定的时间&#xff0c;但是为了不影响客户端的体验&#xff0c;选择异步执行 案例&#xff1a; 首先创建一个service&#xff1a; Service public class AsyncService {public void hello(){try {Threa…

如何在Android中自定义property

在Android中创建自定义的属性&#xff08;Android property&#xff09;通常用于调试、性能调优或传递应用和系统之间的信息。 以下是如何在Android中创建和使用自定义属性的步骤&#xff1a; 1. 定义属性 在Android中&#xff0c;属性是以“属性名称属性值”形式定义的键值对…

SSH实验5密钥登录Linuxroot用户(免密登录)

当用户尝试通过SSH连接到远程服务器时&#xff0c;客户端会生成一对密钥&#xff1a;公钥和私钥。公钥被发送到远程服务器&#xff0c;并存储在服务器的~/.ssh/authorized_keys文件中。而私钥则由客户端保管&#xff0c;不会传输给服务器。 在连接过程中&#xff0c;客户端使用…

CelebV-Text——从文本生成人脸视频的数据集

概述 近年来&#xff0c;生成模型在根据文本生成和编辑视频方面受到了广泛关注。然而&#xff0c;由于缺乏合适的数据集&#xff0c;生成人脸视频领域仍然是一个挑战。特别是&#xff0c;生成的视频帧质量较低&#xff0c;与输入文本的相关性较弱。在本文中&#xff0c;我们通…

天地图入门|标注|移动飞行|缩放,商用地图替换

“天地图”是国家测绘地理信息局建设的地理信息综合服务网站。集成了来自国家、省、市&#xff08;县&#xff09;各级测绘地理信息部门&#xff0c;以及相关政府部门、企事业单位 、社会团体、公众的地理信息公共服务资源&#xff0c;如果做的项目是政府部门、企事业单位尽量选…

Python、Delphi 和 C++ 复制文件速度比较

比较 Python、Delphi 和 C 在文件处理上的速度&#xff0c;可以分为以下几个方面进行测试和分析&#xff1a;文件读写速度&#xff1a;指的是在这三种语言中执行相同的文件读写操作所花费的时间。文件大小影响&#xff1a;不同语言对小文件和大文件的处理是否有显著不同。并发性…