LC20. 有效的括号

用来熟悉一下栈的应用之括号匹配

题目链接

下面是大致思路
1.初始化:创建一个空栈,用于存储左括号。(LC这题不用,自己写完整的需要)
2.遍历字符串:从左到右依次扫描字符串中的每个字符。
3.处理左括号:如果是左括号,将其压入栈中。
4.处理右括号:如果是右括号,检查找顶元素是否与其匹配:

  • 如果匹配,弹出栈顶元素。
  • 如果不匹配,返回false,表示括号不匹配。

5.检查栈是否为空:

  • 遍历结束后,检查找是否为空。
  • 如果栈为空,表示所有括号匹配;否则,返回false。
    (还有就是一开始可以直接排除掉奇数个的情况,不可能匹配

可运行版

下面就是注意一个地方

pairs函数,在扫描的时候如果发现是左括号,那么会进入后面的else逻辑,让左括号入栈
如果发现是右括号
那么会返回与之匹配的左括号,去和当前栈顶的左括号匹配

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

// 定义一个函数 pairs,用于返回与右括号对应的左括号
char pairs(char a)
{
    if (a == '}')
        return '{';
    if (a == ']')
        return '[';
    if (a == ')')
        return '(';
    return 0;
}

// 检查括号是否匹配的函数
bool isValid(char *s)
{
    int n = strlen(s); // 获取字符串的长度
    if (n % 2 == 1)
    { // 如果字符串长度是奇数,不可能匹配
        return false;
    }

    int *stk = (int *)malloc((n + 1) * sizeof(int)); // 动态分配栈的大小
    if (stk == NULL)
    {
        printf("Memory allocation failed\n");
        return false;
    }

    int top = 0; // 初始化栈顶指针
    int i;       // 将变量声明移到循环外部
    for (i = 0; i < n; i++)
    {
        char ch = pairs(s[i]); // 获取与当前字符对应的左括号
        if (ch)
        { // 如果当前字符是右括号
            if (top == 0 || stk[top - 1] != ch)
            {              // 检查栈是否为空或栈顶元素是否匹配
                free(stk); // 释放动态分配的内存
                return false;
            }
            top--; // 弹出栈顶元素
        }
        else
        {                      // 如果当前字符是左括号
            stk[top++] = s[i]; // 将左括号压入栈中
        }
    }

    bool result = (top == 0); // 如果栈为空,表示所有括号匹配
    free(stk);                // 释放动态分配的内存
    return result;
}

// 示例使用
int main()
{
    printf("%d\n", isValid("()"));     // 输出: 1 (true)
    printf("%d\n", isValid("()[]{}")); // 输出: 1 (true)
    printf("%d\n", isValid("(]"));     // 输出: 0 (false)
    printf("%d\n", isValid("([)]"));   // 输出: 0 (false)
    printf("%d\n", isValid("{[]}"));   // 输出: 1 (true)
    // 复杂的例子
    printf("%d\n", isValid("{[()]}"));       // 输出: 1 (true)
    printf("%d\n", isValid("{[(])}"));       // 输出: 0 (false)
    printf("%d\n", isValid("{{[[(())]]}}")); // 输出: 1 (true)
    return 0;
}

cpp


#include <iostream>
#include <stack>
#include <string>
using namespace std;
class Solution
{
public:
    bool isMatch(char a, char b)
    {
        if ((a == '(' && b == ')') || (a == '[' && b == ']') || (a == '{' && b == '}'))
        {
            return true;
        }
        return false;
    }
    bool isValid(string s)
    {
        stack<char> stk; // 定义一个栈,用来存放左括号
        // stack是一个容器适配器,它提供了一种先进后出的数据结构,即栈。只能在栈顶进行插入和删除操作。
        if (s.size() % 2 == 1)
            return false; // 如果字符串长度为奇数则不可能有效,直接返回false;
        for (int i = 0; i < s.size(); i++)
        {   
            // 扫描字符串,遇到左括号入栈,遇到右括号则与栈顶元素匹配;
            if (s[i] == '(' || s[i] == '[' || s[i] == '{')
                stk.push(s[i]); // 遇到左括号入栈;
            // 下面的两个else if 和 else都是对右括号情况的处理
        
            else if (stk.empty())
                return false; // 如果遇到了右括号但是栈已经空了,说明不是有效的括号,直接返回false;
            else if (!isMatch(stk.top(), s[i]))
                return false; // 如果遇到右括号且栈不为空,但是栈顶不是相匹配的左括号,返回false;
            else
                stk.pop(); // 当前遍历到的右括号与栈顶左括号相匹配,弹出栈顶元素继续遍历;
        }
        return stk.empty(); // 遍历结束后,栈为空则为有效,否则无效;
    }
};

int main()
{
    Solution s;
    cout << s.isValid("()") << endl;     // 输出: 1 (true)
    cout << s.isValid("()[]{}") << endl; // 输出: 1 (true)
    cout << s.isValid("(]") << endl;      // 输出: 0 (false)
    return 0;
}

LC版

C++版
在这里插入图片描述
注意 两个empty的不同
比如具体的例子如下

在这里插入图片描述

class Solution {
public:
    bool isMatch(char a,char b)
    {
        if(a == '(' && b == ')' ||a == '[' && b == ']'||a == '{' && b == '}')
            return true;
        else
            return false;
    }
    bool isValid(string s) {
        int n = s.size();
        if (n % 2 == 1) {
            return false;
        }

        stack<char> stk;
        for(int i = 0; i < n ; i++)
        {
            if(s[i]=='(' || s[i]=='[' || s[i]=='{' )
                stk.push(s[i]);
        
            else if(stk.empty())
                return false;
            else if(!isMatch(stk.top(),s[i]))
                return false;
            else if(isMatch(stk.top(),s[i]))
                stk.pop();
            
        }
        return stk.empty(); // 遍历结束后,栈为空则为有效,否则无效;

    }

      

};

C版

char pairs(char a) {
    if (a == '}') return '{';
    if (a == ']') return '[';
    if (a == ')') return '(';
    return 0;
}

bool isValid(char* s) {
    int n = strlen(s);
    if (n % 2 == 1){
        return false;
    }

    int stk[n + 1], top = 0;
    for (int i = 0; i < n; i++)
    {
        char ch = pairs(s[i]);
        if(ch) // 如果是右括号
        {
            if ( top == 0 || stk[top - 1] != ch) {
                // 如果是空栈或者不匹配
                return false;
            }

            top --; // 匹配了就要出栈了(top--指向新的位置)
        }
        else  //如果是左括号就入栈
        {
            //一开始top是0,那么先赋值再移动指针指向下一个位置
            stk[top] = s[i];
            top++;
        }

    }

    return top == 0; //最后应该都出栈了
}

//总结:其实就是把哪些不成立的条件先列出来,还有注意各种边界条件,然后理解了算法原理,就能写出代码了

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

C# 企业微信机器人推送消息 windows服务应用程序的使用

C# 企业微信机器人推送消息 先添加一个机器人! 然后查看机器人就可以得到一个 webhook 特别特别要注意&#xff1a;一定要保护好机器人的webhook地址&#xff0c;避免泄漏&#xff01; 然后开始写代码 &#xff0c;只需要httpPost 调用一下这个地址就可以发送消息了。 首先我…

ctfshow(159->162)--文件上传漏洞

Web159 考点&#xff1a; 前端校验MIME验证黑名单 思路&#xff1a; 上传.user.ini文件&#xff1a; 文件内容auto_prepend_fileshell.png 由于网页存在前端过滤&#xff0c;只允许上传.png文件,所以我们将文件名修改为.user.ini.png上传&#xff0c;然后抓包删除.png后缀名…

《模拟电子技术基础》第六版PDF课后题答案详解

《模拟电子技术基础》第六版是在获首届全国优秀教材建设奖一等奖的第五版的基础上&#xff0c;总结6年来的教学实践经验修订而成的新形态教材。为满足国家人才培养的需求&#xff0c;适应新型教学模式&#xff0c;并考虑到大多数院校逐渐减少课程学时的现状&#xff0c;在不降低…

ComfyUI EcomID: 阿里开源助力定制化个性图像生成,单图生成高相似度图像

❤️ 如果你也关注大模型与 AI 的发展现状&#xff0c;且对大模型应用开发非常感兴趣&#xff0c;我会快速跟你分享最新的感兴趣的 AI 应用和热点信息&#xff0c;也会不定期分享自己的想法和开源实例&#xff0c;欢迎关注我哦&#xff01; &#x1f966; 微信公众号&#xff…

LabVIEW涡扇发动机加力泵测试

LabVIEW软件开发的涡扇发动机加力泵测试平台采用高度集成的硬件设备&#xff0c;实现了对涡扇发动机加力泵的全面测试和分析&#xff0c;从而确保其性能满足严格的航空标准。 项目背景 涡扇发动机是现代飞机的重要动力来源之一&#xff0c;其加力泵的性能直接影响飞机的整体动…

关于我的数据库——MySQL——第二篇

&#xff08;叠甲&#xff1a;如有侵权请联系&#xff0c;内容都是自己学习的总结&#xff0c;一定不全面&#xff0c;仅当互相交流&#xff08;轻点骂&#xff09;我也只是站在巨人肩膀上的一个小卡拉米&#xff0c;已老实&#xff0c;求放过&#xff09;。 表的操作 创建表…

练习LabVIEW第二十八题

学习目标&#xff1a; 刚学了LabVIEW&#xff0c;在网上找了些题&#xff0c;练习一下LabVIEW&#xff0c;有不对不好不足的地方欢迎指正&#xff01; 第二十八题&#xff1a; 建立一个VI&#xff0c;模拟滚动—个骰子(骰子取值1~6)&#xff0c;跟踪骰子滚动后的取值出现次数…

xhr的readyState和status

XMLHttpRequest&#xff08;XHR&#xff09;对象中的readyState和status用于监控异步 HTTP 请求的状态。它们分别表示请求的当前阶段和服务器的响应状态。 readyState 用于判断请求所处的阶段&#xff0c;确保数据完全接收。 status 用于判断请求的结果状态&#xff08;如200表…

计算机网络IP地址分类,子网掩码,子网划分复习资料

IP 地址的概念 IP 地址是独立于硬件地址的逻辑地址&#xff0c;它是由软件提供的地址。 IP 地址是网络层地址。 IP 编址方案和分类 IP 地址由 32 位二进制数构成&#xff0c;分为前缀(网络地址)和后缀(主机地址) 同一网段中每台计算机的 IP 地址是唯一的网络地址的分配全球…

【Stable Diffusion】

1、SD 模型 安装完SD软件后&#xff0c;必须搭配基础模型才能使用。 不同的基础模型&#xff0c;其画风和擅长的领域会有侧重。 Checkpoint大模型 大模型是 SD 的核心&#xff0c;用来控制生成图片的整个画面风格走势。 出图前要选择好合适的大模型&#xff0c;比如有些擅长…

WPF+MVVM案例实战(一)- 设备状态LED灯变化实现

文章目录 1、项目创建2、UI界面布局1. MainWindow.xaml2、颜色转换器实现2.MainViewModel.cs 代码实现3、运行效果4.源代码下载1、项目创建 打开 VS2022 ,新建项目 Wpf_Examples,创建各层级文件夹,安装 CommunityToolkit.Mvvm 和 Microsoft.Extensions.DependencyInjectio …

node集成redis (教学)

文章目录 前言一、安装redis二、可视化界面测试连接1.vscode安装插件 三、node代码编写1.先安装两个库&#xff08;redis和ioredis&#xff09;2.测试连接 &#xff08;前提是你的redis服务器要启动起来&#xff09; 总结 前言 在Node.js中集成ioredis是一个常见的做法&#x…

Java MySQL-JDBC编程

文章目录 初始JDBCJDBC的工作原理 初始MavenMaven入门简介修改Maven的配置文件在idea中查看当前的maven使用在当前Maven工程中加载数据库驱动 DriverManager连接方案注册一个驱动创建一个连接获取一个操作SQL的对象创建SQL查询获取结果集遍历结果集输出结果关闭资源以及完整代码…

TCP全连接队列与 tcpdump 抓包

&#x1f351;个人主页&#xff1a;Jupiter. &#x1f680; 所属专栏&#xff1a;计算机网络高效通关之路 欢迎大家点赞收藏评论&#x1f60a; 目录 listen第二个参数详解 全连接队列与半连接队列半开放连接队列&#xff08;SYN队列&#xff09;全连接队列&#xff08;接受队列…

20241030在荣品PRO-RK3566开发板的适配Rockchip原厂的buildroot的时候配置DTS中的电源域

20241030在荣品PRO-RK3566开发板的适配Rockchip原厂的buildroot的时候配置DTS中的电源域 2024/10/30 17:38 请问 RK3566开发板上的 电源配置 和 DTS文件是如何对应的&#xff1f; 底板原理图 PRO-RK3566-B-20210329原理图.pdf vccio4-supply 是1.8V。 对不上呀&#xff1f; Z:…

【Java】数组的定义与使用

数组的定义与使用 1. 数组的基本概念1.1 为什么要使用数组1.2 什么是数组1.3 数组的创建及初始化1.3.1 数组的创建1.3.2 数组的初始化 1.4 数组的使用1.4.1 数组中元素访问1.4.2 遍历数组 2. 数组是引用类型2.1 初始JVM的内存分布2.2 基本类型变量与引用类型变量的区别2.3 再谈…

活动回顾丨艾体宝《开源软件供应链安全的最佳实践》线下研讨会圆满落幕!

10月&#xff0c;艾体宝联合Mend成功举办了一场主题为“开源软件供应链安全最佳实践”的研讨会。此次活动吸引了众多业内专家、技术领袖和企业代表参与&#xff0c;共同探讨在当今数字化转型浪潮中&#xff0c;企业如何应对开源软件供应链安全的挑战。会议围绕三大核心议题展开…

复现第一周24

1.[SWPUCTF 2021 新生赛]gift_F12 1&#xff09;打开题目 2&#xff09;看源码 3&#xff09;直接ctrl&#xff0b;f搜索flag 2.[SWPUCTF 2021 新生赛]nc签到 1&#xff09;开题 2&#xff09;下载附件用记事本打开 3&#xff09;打开kali使用nc连接代码 输入l\s命令绕过黑名…

如何写出爆款脚本,很多人都忽略了这一项——口语化

不是每次写的视频脚本都绞尽脑汁吗&#xff1f; 你让观众觉得在和你‘聊天’&#xff0c;可一开写就生长硬、平淡、没有吸引力&#xff1f; 其实&#xff0c;只要掌握一些口语化的写作技巧&#xff0c;剧本也能写得像聊天一样轻松自然&#xff0c;让观众从头尾看到&#xff0…

ubuntu 22.04网线连接无ip、网络设置无有线网界面(netplan修复)

目前遇到过树莓派和其他设备安装 ubuntu22.04&#xff0c; 使用有线网络一段时间&#xff08;可能有其他软件安装导致&#xff09;造成有线网络未启动无ip分配的问题。 1、动态分配 通过命令行启动dhcpclient实现 网络eth0存在异常&#xff0c;网口灯电源和信号灯均点亮&am…