• 括号匹配


    括号匹配这个问题,说难好难,但是说简单好像也挺简单,主要就是看我们的思路是否清晰,条例是否清楚。

    基本问题是:给定一串字符,可能包括括号、数字、字母、标点符号、空格,检查这一串字符中的( ) ,[ ],{ }是否匹配,匹配输出yes,反之输出no。

    我们可以先确定最基本的逻辑,就是对输入的数一一判断,如果是左括号就存起来,等到有有括号的时候进行配对,配对成功继续输入,错了就可以退出了。

    于是,数据结构自然而然就是用栈了,而我用的是顺序栈。

    先说说我最开始的想法啦。

    1. 由于首先要读入一串字符,而且包括空格,但是判断的时候只能一个一个判断,所以就先给个数组存这串字符,用下标表示单个字符。

    2. 然后为了方便地控制循环,我用strlen取得了字符的长度。

    3. 设置了一个result参数,用于表示括号是否匹配的状态,1表示匹配成功,0表示不匹配。并将其初始化为1,这样可以避免额外讨论字符串中没有括号的情况。(没有括号也算匹配成功)

    4. 接下来就是匹配环节了。遍历我们之前的数组,遇到左括号入栈;遇到右括号,把这个右括号和出栈的值尝试匹配,成功就继续扫描,失败不用扫描了,直接输出no吧。但是由于我用result表示是否匹配,所以我选择吧result的值变为0,然后退出循环。

    5. 遍历的循环结束后,判断是否匹配,即判断result为0还是为1。

    看起来没啥问题,但接着考虑一下,由于我的result初值为1,即默认匹配,会不会存在一种情况使括号即使不匹配,但是由于没有改变result的值而导致错误呢?

    那么来看看什么时候result会改变。仅当扫描到右括号才会进行匹配尝试,而仅当匹配失败才会使result为0。也就是说,不扫描到右括号,result是没机会匹配的。

    于是我们会想,只有左括号呢?如果没有对应的右括号,即使不匹配,result仍然为1。

    那么就必须额外加一个条件来排除上述情况。显然这种情况下,栈中一定有左括号,即栈一定非空。那么反过来说,如果括号匹配,栈就一定为空。于是想到最后判断匹配的条件是:result=1且栈为空。

    关键代码如下:

     1 cin.getline(a, 100);
     2     length = strlen(a);        
     3     for (int i = 0; i <= length; i++) {        //
     4         if (a[i] == '(' || a[i] == '[' || a[i] == '{') {        //左括号入栈
     5             Push(stack, a[i]);
     6         }
     7         else if (a[i] == ')' || a[i] == ']' || a[i] == '}') {    //右括号,将其与出栈的字符尝试匹配
     8             temp = Pop(stack);                                
     9             if (!((a[i] == ')'&&temp =='(' )|| (a[i] == ']'&&temp == '[') || (a[i] == '}'&&temp == '{'))) {
    10                 result = 0;            //如果不匹配就将result赋0
    11                 break;
    12             }
    13         }
    14     }
    15     if (result == 1&&stack.base==stack.top) {        //匹配一定栈空,排除无右括号匹配,只有左括号
    16         cout << "yes";
    17     }
    18     else {
    19         cout << "no";
    20     }

    需要注意的是,栈顶指针所指的一直是顶元素的上一个。因此入栈的时候,现赋值再让栈顶指针+1;而出栈要反过来,先-1再赋值。一开始我先输出头指针的内容再让头指针减一,这就导致运行时错误。因为我忘了头指针为栈顶+1,因此其所指没有确切的值,导致非法访问。

  • 相关阅读:
    使用zinnia制作android手写输入功能(上)编译zinnia
    Raphael实例
    正则表达式 笔记
    已知弧长和弦长求半径
    Raphael参考 翻译完毕
    在chorme中查找多余的css规则
    CSS3中Transform
    手机移动端WEB资源整合
    JS判断移动设备最佳方法 并实现跳转至手机版网页
    让IE和Firefox兼容的CSS技巧集合css hack
  • 原文地址:https://www.cnblogs.com/luoyang0515/p/10605065.html
Copyright © 2020-2023  润新知