基础数据结构之堆栈

堆栈的定义、入栈、出栈、查询栈顶

#include <stdio.h>
#include <stdlib.h>typedef int DataType;// 定义栈节点结构体
struct StackNode;struct StackNode {DataType data;              // 节点数据struct StackNode* next;     // 指向下一个节点的指针
};// 定义栈结构体
struct Stack {struct StackNode* head;     // 栈顶节点指针int size;                   // 栈的大小(元素数量)
};// 将元素压入栈中
void StackPushStack(struct Stack* stk, DataType dt) {struct StackNode* vtx = (struct StackNode*)malloc(sizeof(struct StackNode));  // 创建新节点vtx->next = stk->head;       // 新节点的下一个节点指针指向栈顶节点vtx->data = dt;              // 设置新节点的数据为传入的数据stk->head = vtx;             // 更新栈顶节点为新节点++stk->size;                 // 增加栈的大小
}// 将栈顶元素弹出栈
void StackPopStack(struct Stack* stk) {struct StackNode* temp = stk->head;   // 临时存储栈顶节点指针stk->head = temp->next;               // 更新栈顶节点为下一个节点free(temp);                           // 释放原栈顶节点的内存--stk->size;                          // 减少栈的大小
}// 获取栈顶元素的值
DataType StackGetTop(struct Stack* stk) {return stk->head->data;     // 返回栈顶节点的数据
}int main() {// 创建一个栈struct Stack myStack;myStack.head = NULL;    // 初始化栈顶节点指针为空myStack.size = 0;       // 初始化栈的大小为0// 将元素压入栈中StackPushStack(&myStack, 10);StackPushStack(&myStack, 20);StackPushStack(&myStack, 30);// 获取栈顶元素并打印DataType top = StackGetTop(&myStack);printf("Top element: %d\n", top);// 从栈中弹出一个元素StackPopStack(&myStack);// 获取新的栈顶元素并打印top = StackGetTop(&myStack);printf("Top element after popping: %d\n", top);return 0;
}

例题1

括号的最大嵌套深度

提示

如果字符串满足以下条件之一,则可以称之为 有效括号字符串valid parentheses string,可以简写为 VPS):

  • 字符串是一个空字符串 "",或者是一个不为 "(" 或 ")" 的单字符。
  • 字符串可以写为 ABA 与 B 字符串连接),其中 A 和 B 都是 有效括号字符串 。
  • 字符串可以写为 (A),其中 A 是一个 有效括号字符串 。

类似地,可以定义任何有效括号字符串 S 的 嵌套深度 depth(S)

  • depth("") = 0
  • depth(C) = 0,其中 C 是单个字符的字符串,且该字符不是 "(" 或者 ")"
  • depth(A + B) = max(depth(A), depth(B)),其中 A 和 B 都是 有效括号字符串
  • depth("(" + A + ")") = 1 + depth(A),其中 A 是一个 有效括号字符串

例如:"""()()""()(()())" 都是 有效括号字符串(嵌套深度分别为 0、1、2),而 ")(" 、"(()" 都不是 有效括号字符串 。

给你一个 有效括号字符串 s,返回该字符串的 s 嵌套深度 。

示例 1:

输入:s = "(1+(2*3)+((8)/4))+1"
输出:3
解释:数字 8 在嵌套的 3 层括号中。

示例 2:

输入:s = "(1)+((2))+(((3)))"
输出:3

提示:

  • 1 <= s.length <= 100
  • s 由数字 0-9 和字符 '+''-''*''/''('')' 组成
  • 题目数据保证括号表达式 s 是 有效的括号表达式

 

#include <stdio.h>
#include <stdlib.h>
typedef struct {char* stack;int top;
} Stack;Stack* createStack(int capacity) {Stack* stack = (Stack*)malloc(sizeof(Stack));stack->stack = (char*)malloc(capacity * sizeof(char));stack->top = -1;return stack;
}void push(Stack* stack, char element) {stack->stack[++stack->top] = element;
}char pop(Stack* stack) {return stack->stack[stack->top--];
}int isEmpty(Stack* stack) {return stack->top == -1;
}                                                                                                    
int maxDepth(char* s) {int maxDepth = 0;int currentDepth = 0;int i = 0;Stack* stack = createStack(100);while (s[i] != '\0') {if (s[i] == '(') {push(stack, s[i]);currentDepth++;if (currentDepth > maxDepth) {maxDepth = currentDepth;}} else if (s[i] == ')') {pop(stack);currentDepth--;}i++;}return maxDepth;
}
int main() {char s[] = "(1+(2*3)+((8)/4))+1";int depth = maxDepth(s);printf("The maximum nesting depth is: %d\n", depth);return 0;
}

例题2

回文链表

给定一个链表的 头节点 head ,请判断其是否为回文链表。

如果一个链表是回文,那么链表节点序列从前往后看和从后往前看是相同的。

示例 1:

输入: head = [1,2,3,3,2,1]
输出: true

示例 2:

输入: head = [1,2]
输出: false

提示:

  • 链表 L 的长度范围为 [1, 105]
  • 0 <= node.val <= 9
#include <stdio.h>
#include <stdbool.h>
#include <stdlib.h>struct ListNode {int val;struct ListNode* next;
};// 创建一个堆栈结构
struct Stack {int* array;int top;int capacity;
};// 初始化堆栈
struct Stack* createStack(int capacity) {struct Stack* stack = (struct Stack*)malloc(sizeof(struct Stack));stack->array = (int*)malloc(capacity * sizeof(int));stack->top = -1;stack->capacity = capacity;return stack;
}// 判断堆栈是否为空
bool isEmpty(struct Stack* stack) {return stack->top == -1;
}// 判断堆栈是否已满
bool isFull(struct Stack* stack) {return stack->top == stack->capacity - 1;
}// 将元素压入堆栈
void push(struct Stack* stack, int value) {if (isFull(stack)) {return;}stack->array[++stack->top] = value;
}// 从堆栈中弹出元素
int pop(struct Stack* stack) {if (isEmpty(stack)) {return -1;}return stack->array[stack->top--];
}// 判断链表是否为回文链表
bool isPalindrome(struct ListNode* head) {if (!head || !head->next) {return true;}// 统计链表的长度int length = 0;struct ListNode* curr = head;while (curr) {length++;curr = curr->next;}// 将链表前半部分的值压入堆栈struct Stack* stack = createStack(length / 2);curr = head;int i = 0; for (i = 0; i < length / 2; i++) {push(stack, curr->val);curr = curr->next;}// 如果链表长度为奇数,跳过中间节点if (length % 2 == 1) {curr = curr->next;}// 比较链表后半部分的值与堆栈中弹出的值是否相等while (curr) {int value = pop(stack);if (value != curr->val) {return false;}curr = curr->next;}return true;
}int main() {// 创建链表 [1, 2, 3, 2, 1]struct ListNode* head = (struct ListNode*)malloc(sizeof(struct ListNode));head->val = 1;head->next = (struct ListNode*)malloc(sizeof(struct ListNode));head->next->val = 2;head->next->next = (struct ListNode*)malloc(sizeof(struct ListNode));head->next->next->val = 3;head->next->next->next = (struct ListNode*)malloc(sizeof(struct ListNode));head->next->next->next->val = 2;head->next->next->next->next = (struct ListNode*)malloc(sizeof(struct ListNode));head->next->next->next->next->val = 1;head->next->next->next->next->next = NULL;bool isPalin = isPalindrome(head);if (isPalin) {printf("The linked list is a palindrome.\n");} else {printf("The linked list is not a palindrome.\n");}// 释放链表的内存struct ListNode* curr = head;while (curr) {struct ListNode* temp = curr;curr = curr->next;free(temp);}return 0;
}

例题3

反转链表

给你单链表的头节点 head ,请你反转链表,并返回反转后的链表。

示例 1:

输入:head = [1,2,3,4,5]
输出:[5,4,3,2,1]

示例 2:

输入:head = [1,2]
输出:[2,1]

示例 3:

输入:head = []
输出:[]

提示:

  • 链表中节点的数目范围是 [0, 5000]
  • -5000 <= Node.val <= 5000
#include <stdio.h>
#include <stdbool.h>
#include <stdlib.h>struct ListNode {int val;struct ListNode* next;
};// 创建一个堆栈结构
struct Stack {int* array;int top;int capacity;
};// 初始化堆栈
struct Stack* createStack(int capacity) {struct Stack* stack = (struct Stack*)malloc(sizeof(struct Stack));stack->array = (int*)malloc(capacity * sizeof(int));stack->top = -1;stack->capacity = capacity;return stack;
}
// 判断堆栈是否为空
bool isEmpty(struct Stack* stack) {return stack->top == -1;
}
// 判断堆栈是否已满
bool isFull(struct Stack* stack) {return stack->top == stack->capacity - 1;
}
// 将元素压入堆栈
void push(struct Stack* stack, int value) {if (isFull(stack)) {return;}stack->array[++stack->top] = value;
}
// 从堆栈中弹出元素
int pop(struct Stack* stack) {if (isEmpty(stack)) {return -1;}return stack->array[stack->top--];
}
// 反转链表
struct ListNode* reverseList(struct ListNode* head) {if (!head || !head->next) {return head;}// 统计链表的长度int length = 0;struct ListNode* curr = head;while (curr) {length++;curr = curr->next;}// 将链表的值压入堆栈struct Stack* stack = createStack(length);curr = head;int i = 0; for (i = 0; i < length; i++) {push(stack, curr->val);curr = curr->next;}// 将堆栈弹出的值给链表 curr = head;while (curr) {curr->val = pop(stack);curr = curr->next;}return head;
} int main() {// 创建链表 [1, 2, 3, 4, 5]struct ListNode* head = (struct ListNode*)malloc(sizeof(struct ListNode));head->val = 1;head->next = (struct ListNode*)malloc(sizeof(struct ListNode));head->next->val = 2;head->next->next = (struct ListNode*)malloc(sizeof(struct ListNode));head->next->next->val = 3;head->next->next->next = (struct ListNode*)malloc(sizeof(struct ListNode));head->next->next->next->val = 4;head->next->next->next->next = (struct ListNode*)malloc(sizeof(struct ListNode));head->next->next->next->next->val = 5;head->next->next->next->next->next = NULL;head=reverseList(head);int i=0;for(i=0;i<5;i++){printf("%d ",head->val);head=head->next;}// 释放链表的内存struct ListNode* curr = head;while (curr) {struct ListNode* temp = curr;curr = curr->next;free(temp);}return 0;
}

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

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

相关文章

不用下载就可以使用的三个在线抠图网站

字图像处理技术的发展&#xff0c;抠图已经成为一项重要的技术。在许多情况下&#xff0c;我们需要将图片中的某一部分抠出来&#xff0c;例如将人物从背景中抠出&#xff0c;或者将产品从图片中抠出。传统的抠图方法需要使用专业的图像处理软件&#xff0c;如Photoshop等&…

php 的数学常用函数

目录 1.常用列表 2.代码示例 1.常用列表 函数名描述输入输出abs()求绝对值数字绝对值数字ceil()进一法取整浮点数进一取整floor()舍去法求整浮点数直接舍去小数部分fmod()浮点数取余 两个浮点 数,x>y 浮点余数 pow()返回数的n次方基础数n次方乘方值round()浮点数四舍五入…

Hive 数据同步

一、需求 同步集团的数据到断直连环境。 二、思路 三、同步数据&#xff08;方案&#xff09; 1、环境&#xff1a;断直连模拟环境 2、操作机器&#xff1a;ETL 机器 XX.14.36.216 3、工作路径&#xff1a;cd /usr/local/fqlhadoop/hadoop/bin 4、执行命令&#xff1a; 命令…

[ctf.show 元旦水友赛 2024] crypto

感觉半个多月回家没有打开过电脑了。看到ctf.show上元旦的比赛&#xff0c;才想起似乎应该看看。 月月的爱情故事 上来这就是个小脑洞题&#xff0c;给了一大段文字和一个base64的串。并且提示&#xff1a;试试摩斯吧&#xff01; 从文字上看只有三种标点符号&#xff0c;显…

设计一个简易版的数据库路由

&#x1f44f;作者简介&#xff1a;大家好&#xff0c;我是爱吃芝士的土豆倪&#xff0c;24届校招生Java选手&#xff0c;很高兴认识大家&#x1f4d5;系列专栏&#xff1a;Spring原理、JUC原理、Kafka原理、分布式技术原理、数据库技术&#x1f525;如果感觉博主的文章还不错的…

大模型在游戏行业的应用分析

文章目录 一、大模型作用1&#xff09;节省美术成本2&#xff09;模仿用户肖像&#xff0c;精准投放3&#xff09;买量流程的自动化4&#xff09;缩短视频素材制作周期5&#xff09;例如新营销形式宣传&#xff08;图生图&#xff09;5&#xff09;故事设计6&#xff09;辅助代…

怎么一边讲PPT一边录视频 如何一边录制PPT一边录制人像 录屏软件免费录屏 PPT录制怎么录制

随着新媒体技术的发展&#xff0c;短视频和直播越来越火。越来越多的小伙伴加入了视频制作的大军&#xff0c;那么你想知道怎么一边讲PPT一边录视频&#xff0c;如何一边录制PPT一边录制人像吗&#xff1f; 一、怎么一边讲PPT一边录视频 我们可以借助PPT本身自带的屏幕录制功能…

Ubuntu 22.04 基础环境搭建

这是Ubuntu软件安装系列的第一篇&#xff0c;我们来聊聊基础环境搭建。 这个专栏主要讲一些常见服务端软件的安装和配置&#xff0c;当然也包括对软件架构和作用的分析&#xff0c;以及使用的场景的介绍。 注意我们这里使用的Ubuntu的版本是22.04&#xff0c;基本上大厂的云服…

短视频账号矩阵剪辑分发系统技术源头开发

1.技术开发必备的开发文档说明&#xff1a; 1.1系统架构&#xff1a; 抖音SEO排名系统主要由以下几个模块组成&#xff1a; 1. 数据采集模块&#xff1a;负责采集抖音上的相关数据&#xff0c;包括视频、用户、话题等。 2. 数据处理模块&#xff1a;对采集到的数据进行处理&a…

Redis如何把字符集的编码格式设置为UTF-8

一、问题复现&#xff08;编码错乱&#xff09; 刚安装好的redis在使用的过程中&#xff0c;若使用到了汉字&#xff0c;则在显示的时候&#xff0c;汉字是不能够正常显示的&#xff0c;因为redis在解析的过程中&#xff0c;会将汉字转换成其他编码的格式&#xff0c;如下图&am…

考研英语高频打卡

高频词汇13——15抽背答案 1、colleague /ˈkɒliːɡ/ 考频20&#xff08;英一12 次&#xff0c;英二8 次&#xff09; n. 同事&#xff0c;同僚 2、despite /dɪˈspaɪt/ 考频19&#xff08;英一12 次&#xff0c;英二7 次&#xff09; prep. 不管&#xff0c;不顾 3、overa…