【LeetCode 1106】Offer 驾到,掘友接招!我正在参与2022春招系列活动-刷题打卡任务

112 阅读1分钟

Offer 驾到,掘友接招!我正在参与2022春招系列活动-刷题打卡任务活动详情

一、题目描述

给定一个bool表达式,如|(&(t,f,t),!(f)),求其值

数据范围

L <= 20000

二、思路分析

典型的字符串表达式的题目,但是之前写双栈操作(数字栈、符号栈)写麻了,所以换一个做法。

观察题目的表达式,每一层都很规范,非常适合写递归。所以这题也就变成了一个递归的大模拟,没什么思维难度,主要在于细节。

这里说几个自己被坑的点

一、切割字符串的时候没有判断层次

我们将第一层内的东西全部看成一个单位,所以我们要将他们切分开来,依次递归、保存,最后求值。这些东西是以逗号‘,’为分隔,但是每个单位里面还可能有逗号,如何判断当前遇到的括号是对应于最外层的用于分隔的逗号呢? 开个count记录一下层次就好了,左括号加一右括号减一,等于零的时候就是我们当前所在的最外的层次。

二、 s.substr()

该函数传参的时候加减号搞反了,单步调的时候才发现。这其实是挺累人的错误,临场的时候很难查出来。

三、

三、AC代码

class Solution {
public:

    bool deal(string s) {
        int l = s.length();
        if (l==1) return s[0]=='t' ? true : false;
        if (s[0]=='!') return !deal(s.substr(2, l-3));

        vector<bool> f;
        int last=1,count=0;
        for (int i=2; i<l; i++){
            if (s[i]=='(') count++;
            if (s[i]==')') count--;
            if ((s[i]==',' && count==0) || i==l-1) {
                f.push_back(deal(s.substr(last+1, i-last-1)));
                last = i;
            }
        }
        int n = f.size();
        for (int i=1; i<n; i++) {
            if (s[0]=='|') f[0] = f[0] | f[i];
                    else f[0] = f[0] & f[i];
        }
        return f[0];
    }

    bool parseBoolExpr(string expression) {
        return deal(expression);
    }
};

四、总结

目前一共接触到了三题表达式的题目,要及时复习及时看,有些坑点真的是一言难尽,还是得注意细节与边界吧。在写之前最好能站在一个宏观的层面设计好布局,能省去很多微操调整的地方。