day2

第一题:有效的括号

本题用到的知识点:栈(stack)和哈希表

题目描述:

 解题思路:
  • 左括号必须以正确的顺序和右括号闭合,比如“[ ( { } ) ] ",这样:[ ( { ) } ] 虽然对应每种左括号都能找到右括号,但是并不能以正确的顺序进行闭合。
  • 最左边的左括号要和最右边的右括号匹配,将左括号从栈中移除,这符合先进后出的顺序。
题解:

1.构建一个哈希表,将括号匹配成键值对存放在哈希表中。

2.使用栈,通过遍历循环字符串将左边的括号压入栈中,将右括号与左括号进行配对看是否成功。

class Solution:
    def isValid(self, s: str) -> bool:
        dic={'(':')','{':'}','[':']','#':'#'}
        stack=['#'] 
        for i in s:
            if i in dic:
                stack.append(i)
            else:
                if dic[stack.pop()]!=i:
                    return False
        return len(stack)==1

 注意点:

如果一开始碰到的是右括号,那需要从栈中弹出一个值和该右括号进行匹配,但如果此时栈(列表)是空的就会报错,所以让栈初始的时候就有一个值,在字典中也有该值的键值对。

复杂度:

最多遍历循环一遍字符串,复杂度为O(n).

第二题:删除最外层的括号

题目:

 题目意思就是要删除最外层的括号,留下里边的。

解题思路:

该题和第一题有相似之处:

准备一个空栈stack和结果字符串str,遍历循环输入的字符串,遇到左括号'(' 入栈,遇到右括号')' 则将栈顶元素弹出。栈从空到空的过程就是遍历循环到一个大括号的过程,我们只需要将最外层括号之外的内容添加到结果字符串str中。

难点:怎样哪个是判断最外层的括号?

最外层的左括号一定是第一个入栈的,此时栈的长度为1,那也一定是最后一个出栈的,此时栈的长度还是1,所以根据栈的长度是否大于1来决定是否要将遍历到的字符添加到结果字符串中。

代码:
class Solution:
    def removeOuterParentheses(self, s: str) -> str:
        str,stack='',[]
        for i in s:
            if i =='(':
                stack.append(i)
            if len(stack)>1:
                str+=i
            if i==')':
                stack.pop()
            
        return str

注意要先判断栈的长度是否大于一,在进行出栈判断。

时间复杂度:

最多只需要遍历循环字符串,时间复杂度为O(n)。

第三题:删除字符串中所有相邻的重复项。

题目:

 解题思路:

1.最开始想使用遍历字符串,看相邻项元素是否相等,如果相等,就删除对应下标的元素。

但是字符串遍历下标都是越来越大,并不能实现。

2.正确解决方法:用栈来解决。遍历循环字符串,将字符串的元素压入栈中,如果栈顶元素和遍历的元素相同,那么将该元素出栈。最后将栈中的元素转化成字符串。

代码:
class Solution:
    def removeDuplicates(self, s: str) -> str:
        stack=['#']
        for i in s:
            if stack[-1]==i:
                stack.pop()
            else:
                stack.append(i)
        res=''.join(stack[1:])
        return res

(第一道没有看题解就写出来的!!)写这个解法的难点就是:刚开始的栈是空的,怎样写条件语句让元素压入栈中,如果直接判断stack[-1]==i ,这个时候列表为空,会发生列表超出范围。所以初始化列表的值不为空。

代码改进:

看了题解发现,可以在判断语句stack[-1]==i 时,再加一项列表不为空,如果列表为空就直接将元素入栈。

class Solution:
    def removeDuplicates(self, s: str) -> str:
        stack=[]
        for i in s:
            if stack and stack[-1]==i:
                stack.pop()
            else:
                stack.append(i)
        res=''.join(stack)
        return res
复杂度:

时间复杂度:O(n)

第四题:删除子串后的字符串的最小长度。

题目:

 题解:

这道题我觉得和括号匹配思路一样,不多赘述。

class Solution:
    def minLength(self, s: str) -> int:
        stack=[]
        for i in s:
            if stack and i=='B':
                if stack[-1]=='A':
                    stack.pop()
                else:
                    stack.append(i)
            elif stack and i=='D':
                if stack[-1]=='C':
                    stack.pop()
                else:
                    stack.append(i)
            else:
                stack.append(i)
        return len(stack)
时间复杂度:O(n)
假设用户输入的 `N` 值为 8,以下是 `else if(N>1)` 部分的运行过程: #### 初始状态 ```c count = 1; day = 2; day1 = 1; day2 = 1; ``` 此时,已经经过了 2 天,当前兔子数量 `count` 为 1。 #### 第一次循环 - `count = day1 + day2`:`count = 1 + 1 = 2` - `day1 = day2`:`day1` 变为 1 - `day2 = count`:`day2` 变为 2 - `day++`:`day` 变为 3 此时,经过了 3 天,当前兔子数量 `count` 为 2。 #### 第二次循环 - `count = day1 + day2`:`count = 1 + 2 = 3` - `day1 = day2`:`day1` 变为 2 - `day2 = count`:`day2` 变为 3 - `day++`:`day` 变为 4 此时,经过了 4 天,当前兔子数量 `count` 为 3。 #### 第三次循环 - `count = day1 + day2`:`count = 2 + 3 = 5` - `day1 = day2`:`day1` 变为 3 - `day2 = count`:`day2` 变为 5 - `day++`:`day` 变为 5 此时,经过了 5 天,当前兔子数量 `count` 为 5。 #### 第四次循环 - `count = day1 + day2`:`count = 3 + 5 = 8` - `day1 = day2`:`day1` 变为 5 - `day2 = count`:`day2` 变为 8 - `day++`:`day` 变为 6 此时,经过了 6 天,当前兔子数量 `count` 为 8,满足 `count >= N` 的条件,循环结束。 最终输出的 `day` 值为 6,表示达到 8 只兔子需要 6 天。 ```c #include<stdio.h> int main() { int N = 8; int day = 0; int day1 = 1; int day2 = 1; int count; if (N == 1) { day = 1; } else if (N > 1) { count = 1; day = 2; while (count < N) { count = day1 + day2; day1 = day2; day2 = count; day++; } } printf("%d", day); return 0; } ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值