数据结构——栈和队列(C语言)

news2024/9/22 7:17:08

栈种常见的数据结构,它用来解决一些数据类型的问题,那么好,我来带着大家来学习一下栈

文章目录

    • 对栈的认识
    • 栈的模拟实现
    • 栈的练习
      • 方法一
      • 方法二

对栈的认识

栈(stack)是限定只能在表的一端进行插入删除操作的线性表

栈是一种先进后出的顺序结构,这里的先进后出就是先进来的数据要后出(跟没说一样)
就是1,2,3,4,5这五个数据,只能从5到1逐个访问。

数据结构栈的定义

栈顶:栈顶元素,最后一个入栈的元素
入栈
出栈
栈空:判断栈是否为空
栈的大小:返回站内元素个数

栈的模拟实现

在了解了栈之后,我们来对它进行简单的实现一下。
首先,我们应该先了解大框架,这里我们用数组的方式进行模拟实现(比较合适的方式,其他的也可以)

我们采用分模块的方式进行实现,这里,我在代码中会进行注释,可直接阅读代码来学习栈的实现。

stack.h用来声明各种头文件。
stack.c用来实现各个功能的实现包括入栈。 出栈等栈的基本功能。
test.h来测试代码功能

stack.h

#pragma once

#include<stdio.h>
#include<stdlib.h>
#include<assert.h>
#include<stdbool.h>

//栈可以村粗不同类型的数据,这里我们直接使用·typedef重定义类型
typedef int stdatetype;

//用结构体来实现栈
typedef struct stack {
	int capacity;//capacity表示栈的容量
	int top;//栈顶元素
	int* a;//数组
}st;//st是重命名的结果



//栈的初始化
void initst(st* pst);

//栈的插入和删除
void pushback(st* pst,stdatetype x);

void popback(st* pst);
void printst(st* pst);

//返回栈顶元素
stdatetype sttop(st* pst);

//返回栈内元素个数
int sizest(st* pst);

//返回栈是否为空
bool empty(st* pst);

//销毁栈
void destroy(st* pst);

stack.c

#include"stack.h"

//初始化栈
void initst(st* pst)
{
	pst->top = -1;//top初始化为-1(这里也可以是零,但下面的代码也需要改动)
	//栈的容量
	pst->capacity = 0;//capacity可扩容
	pst->a = NULL;//对数组a进行制空
}

//入栈
void pushback(st* pst,stdatetype x)
{
	assert(pst);//断言,以防止pst是一个空指针

	if ((pst->top + 1) == pst->capacity)//判断,如果top+1等于栈的容量的
	话,就要进行扩容
	{
		pst->capacity = pst->capacity == 0 ? 4 : pst->capacity * 2;
		stdatetype* tail = (stdatetype*)realloc(pst->a, sizeof(stdatetype)*pst->capacity);

		assert(tail);//断言一下,如果扩容失败,终止程序
		pst->a = tail;//扩容成功,把地址给a
	}

	pst->a[++(pst->top)] = x;//入栈
}

//出栈
void popback(st* pst)
{
	assert(pst);
	//如果栈为空,终止程序
	assert(pst->top > -1);

	pst->top--;
}


//返回栈顶元素
stdatetype sttop(st* pst)
{
	assert(pst);
	//栈为空终止程序
	assert(pst->top > -1);

	return pst->a[pst->top];//返回栈顶元素
}

//返回栈的大小
int sizest(st* pst)
{
	assert(pst);

	return pst->top + 1;
}

//判断栈是否为空
bool empty(st* pst)
{
	assert(pst);

	return pst->top == -1;//直接进行判断
}

//销毁栈
void destroy(st* pst)
{
	assert(pst);

	free(pst->a);
	pst->a = NULL;
	pst->top = -1;
	pst->capacity = 0;

}

test.c

#include"stack.h"

int main()
{
	st s;
	initst(&s);
	pushback(&s, 1);
	pushback(&s, 2);
	pushback(&s, 3);

	printf("%d", sizest(&s));
	popback(&s);
	while (s.top > -1)
		printf("%d--", s.a[s.top--]);//因为栈的特点,要这样对栈进行打印


	if (empty(&s))
		printf("\n空");
	destroy(&s);


	return 0;
}

好了,栈是比较简单的数据结构,学习到这里,相信你也已经对栈有了一定的了解,

栈的练习

下面我们来做一道题,趁热打铁一下
https://leetcode.cn/problems/valid-parentheses/description/

在这里插入图片描述
这是这道题的要求
在这里插入图片描述

这道题就非常适合使用栈来解决,当我们学完C++之后,stl库的使用会让我们更轻松的解决这道题,但是我们这里也有解决方法,我们可以直接把上面的模拟实现,稍做修改拿来使用

这里我·提供两种方法(都可以通过)

方法一

下面是这道题的代码,大部分都是在实现栈,当我们学习过C++stl之后,这就会非常简单

bool isValid(char* s) {
    #include<stdio.h>
#include<stdlib.h>
#include<assert.h>
#include<stdbool.h>
    typedef char stdatetype;

//用结构体来实现栈
typedef struct stack {
	int capacity;//capacity表示栈的容量
	int top;//栈顶元素
	stdatetype* a;//数组
}st;//st是重命名的结果


void initst(st* pst)
{
	pst->top = -1;//top初始化为-1(这里也可以是零,但下面的代码也需要改动)
	//栈的容量
	pst->capacity = 0;//capacity可扩容
	pst->a = NULL;//对数组a进行制空
}

//入栈
void pushback(st* pst,stdatetype x)
{
	assert(pst);//断言,以防止pst是一个空指针

	if ((pst->top + 1) == pst->capacity)//判断,如果top+1等于栈的容量的
	//话,就要进行扩容
	{
		int newcapacity = pst->capacity == 0 ? 4 : pst->capacity * 2;
		stdatetype* tail = (stdatetype*)realloc(pst->a, sizeof(stdatetype)*newcapacity);

		assert(tail);//断言一下,如果扩容失败,终止程序
		pst->a = tail;//扩容成功,把地址给a

        pst->capacity=newcapacity;
	}

	pst->a[++(pst->top)] = x;//入栈
}

//出栈
void popback(st* pst)
{
	assert(pst);
	//如果栈为空,终止程序
	assert(pst->top > -1);

	pst->top--;
}


//返回栈顶元素
stdatetype sttop(st* pst)
{
	assert(pst);
	//栈为空终止程序
	assert(pst->top > -1);

	return pst->a[pst->top];//返回栈顶元素
}

//返回栈的大小
int sizest(st* pst)
{
	assert(pst);

	return pst->top + 1;
}

//判断栈是否为空
bool empty(st* pst)
{
	assert(pst);

	return pst->top == -1;//直接进行判断
}

//销毁栈
void destroy(st* pst)
{
	assert(pst);

	free(pst->a);
	pst->a = NULL;
	pst->top = -1;
	pst->capacity = 0;

}
    st _st;
	initst(&_st);
    while(*s)
    {
        char ch=*s;
        if(ch=='{'||ch=='('||ch=='[')
        {
            pushback(&_st,ch);
        }
        else
        {
            if(_st.top==-1){
                destroy(&_st);//防止内存泄露
                return false;
            }
            if((ch=='}'&&sttop(&_st)!='{')||
            (ch==')'&&sttop(&_st)!='(')||
            (ch==']'&&sttop(&_st)!='['))
            {
                destroy(&_st);
                return false;
            }
            popback(&_st);
        }
        s++;
    }
    if(!empty(&_st)){
        destroy(&_st);
        return false;
    }
    destroy(&_st);
    return true;
}

方法二

这样的实现过于麻烦,我们也有另一种方法,用数组快速的模拟栈
直接看代码吧

bool isValid(char* s) {
    const int N = 10010;
    int st[N];
    int hh=0;
    while(*s)
    {
        char top=*s;
        if(top=='{'||top=='('||top=='[')
        {
            st[hh++]=top;
        }
        else
        {
            if(hh==0)
                return false;
            if((top=='}'&&st[hh-1]!='{')||
            (top==')'&&st[hh-1]!='(')||
            (top==']'&&st[hh-1]!='['))
            {
                return false;
            }
            hh--;
        }
        s++;
    }
    if(hh)
    {
        return false;
    }
    return true;
}

栈的学习就先到这里了,各位有什么不同见解可以说出来,一起交流一下

感谢观看,有错误请指出

在这里插入图片描述

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

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

相关文章

苍穹外卖项目可以写的简历和如何优化简历

文章目录 重点写中规写添加自己个性的项目面试会问道的问题 我是一名双非大二计算机本科生&#xff0c;希望我的分享对你有帮助&#xff0c;点赞关注不迷路。 简历编写一直是很多人求职人的心病&#xff0c;我自己上学期有一门课程是去校内企业面试&#xff0c;当时我就感受出…

性能脚本设计

性能脚本设计 目标 - 性能脚本设计技巧 1. 为什么要设计性能脚本&#xff1f; 1.1 需求 100虚拟用户对(查询学院-所有)接口测试&#xff0c;以每秒启动10个用户,统计服务器平均响应时间和错误率1.2 问题 100虚拟用户请求服务器的时候&#xff0c;如何统计服务器响应时间和…

Unity_Timeline使用说明

Unity_Timeline使用说明 首先要找到工具吧&#xff1f;Unity2023.1.19f1c1打开如下&#xff1a; &#xff08;团结引擎没找见哪儿打开&#xff0c;可能是引擎问题吧&#xff1f;有知道的同学可以告诉我在哪儿打开&#xff09; Timelime使用流程&#xff1a; 打开之后会提示您…

18.通过telepresence调试部署在Kubernetes上的微服务

Telepresence简介 在微服务架构中,本地开发和调试往往是一项具有挑战性的任务。Telepresence 是一种强大的工具,使得开发者本地机器上开发微服务时能够与运行在 Kubernetes 集群中的其他服务无缝交互。本文将深入探讨 Telepresence 的架构、运行原理,并通过实际的案例演示其…

Python XPath解析html出现⋆解决方法 html出现#123;解决方法

前言 爬网页又遇到一个坑&#xff0c;老是出现乱码&#xff0c;查看html出现的是&#数字;这样的。 网上相关的“Python字符中出现&#的解决办法”又没有很好的解决&#xff0c;自己继续冲浪&#xff0c;费了一番功夫解决了。 这算是又加深了一下我对这些iso、Unicode编…

HarmonyOS使用Web组件加载页面

1、加载网络页面 在Web组件创建时&#xff0c;指定默认加载的网络页面 。在默认页面加载完成后&#xff0c;如果开发者需要变更此Web组件显示的网络页面&#xff0c;可以通过调用loadUrl()接口加载指定的网页。 默认在Web组件加载完“www.baidu.com”页面后&#xff0c;点击按…

flask_django基于python的城市轨道交通公交线路查询系统vue

同时&#xff0c;随着信息社会的快速发展&#xff0c;城市轨道交通线路查询系统面临着越来越多的信息&#xff0c;因此很难获得他们对高效信息的需求&#xff0c;如何使用方便快捷的方式使查询者在广阔的海洋信息中查询&#xff0c;存储&#xff0c;管理和共享信息方面有效&…

python fastapi swagger 连接超时

问题描述 运行python项目时&#xff0c;访问fastapi swagger出现连接超时。 https://cdn.jsdelivr.net/npm/swagger-ui-dist4/swagger-ui.css https://cdn.jsdelivr.net/npm/swagger-ui-dist4/swagger-ui-bundle.js 解决方案 第一步 下载文件 https://pan.baidu.com/s/1Ef…

微信小程序如何实现点击上传图片功能

如下所示,实际需求中常常存在需要点击上传图片的功能,上传前显示边框表面图片显示大小,上传后将图形缩放到边框大小。 实现如下: .wxml <view class="{{img_src==?blank-area:}}" style="width:100%;height:40%;display:flex;align-items: center;jus…

K8S之Pod的介绍和使用

Pod的理论和实操 pod理论说明Pod介绍Pod运行与管理Pod管理多个容器Pod网络Pod存储 Pod工作方式自主式Pod控制器管理的Pod&#xff08;常用&#xff09; 创建pod的流程 pod实操通过资源清单文件创建自主式pod通过kubectl run创建Pod&#xff08;不常用&#xff09; pod理论说明 …

springboot整合mqtt实现消息订阅和推送

前言 mica-mqtt-client-spring-boot-starter是一个基于Spring Boot的MQTT客户端启动器&#xff0c;它集成了mica-mqtt客户端&#xff0c;提供了在Spring Boot应用程序中使用MQTT协议进行消息通信的能力。以下是关于mica-mqtt-client-spring-boot-starter的简介&#xff1a; 特…

Spring-boot项目+Rancher6.3部署+Nacos配置中心+Rureka注册中心+Harbor镜像仓库+NFS存储

目录 一、项目概述二、环境三、部署流程3.1 Harbor部署3.1.1 docker安装3.1.2 docker-compose安装3.1.3 安装证书3.1.4 Harbor下载配置安装 3.2 NFS存储搭建3.3 Rancher平台配置3.3.1 NFS存储相关配置3.3.2 Harbor相关配置3.3.3 Nacos部署及相关配置3.3.4 工作负载deployment配…

在 Android 中使用 C/C++:初学者综合指南

在 Android 中使用 C/C&#xff1a;初学者综合指南 一、为什么有人在他们的 Android 项目中需要 C/C 支持&#xff1f;二、了解 C 如何集成到 Android 应用程序中三、C和Java程序的编译3.1 Java3.2 Android ART 和 DEX 字节码 四、使用 JNI 包装 C 源代码五、CMake和Android ND…

326. Power of Three(3 的幂)

题目描述 给定一个整数&#xff0c;写一个函数来判断它是否是 3 的幂次方。如果是&#xff0c;返回 true &#xff1b;否则&#xff0c;返回 false。 整数 n 是 3 的幂次方需满足&#xff1a;存在整数 x 使得 n 3 x n 3^x n3x 问题分析 要证明一个整数是三的幂次方&#…

【计算机网络】【练习题及解答】【新加坡南洋理工大学】【Computer Control Network】

说明&#xff1a; 仅供学习使用。 一、题目描述 题目共4问&#xff0c;描述网络通信中的 帧传输时延&#xff08;Frame Delay&#xff09;、传播时延&#xff08;Propagation Delay&#xff09;&#xff0c;以及 链接利用率&#xff08;Link Utilization&#xff09; 的相关…

《游戏-03_2D-开发》

基于《游戏-02_2D-开发》&#xff0c; 继续制作游戏&#xff1a; 首先要做的时切割人物Idle空闲状态下的动画&#xff0c; 在切割之前我们需要创建一个文件夹&#xff0c;用来存放动画控制器AnimatorContoller&#xff0c; 再创建一个人物控制器文件夹用来存放人物控制器&…

当前的人工智能忽略了人类最具有灵性的心理部分

在人工智能的发展中&#xff0c;目前人工智能的侧重点主要是在物理机理与数理符号计算方面。 物理机理是指人工智能系统对现实世界的感知和交互能力。例如&#xff0c;通过传感器和摄像头等设备获取环境信息&#xff0c;以及利用机器学习和深度学习等技术进行数据分析和模式识别…

pve宿主机更改网络导致没网,pve更改ip

一、问题描述 快过年了&#xff0c;我把那台一直在用的小型服务器&#xff0c;带回去了&#xff0c;导致网络发生了变更&#xff0c;需要对网络进行调整&#xff0c;否则连不上网&#xff0c;我这里改的是宿主机&#xff0c;不是pve虚拟机中的系统。 二、解决方法 pve用的是…

AutoDL----VScode远程ssh连接

1、首先安装ssh插件 首先安装插件&#xff0c;在商店里抖索remote-ssh 2、建立连接 安装完成后在插件栏就会看到远程连接这一栏 点击添加后会让你输入ssh的地址&#xff0c;直接复制AutoDL的&#xff0c;按下Enter&#xff0c;选择第一个配置文件 选择Linux平台 继续后…

8-Docker网络模式之none

1.介绍 Docker none网络模式下,虽然Docker容器拥有自己的Network Namespace,但是Docker容器不会进行任何网络配置,即:Docker容器没有网卡,IP地址等信息,只有lo回环网络。由于这种类型的网络没有办法联网,所以封闭的网络能很好的保证Docker容器的安全性。 2.原理 Dock…