【leetcode】字符串解码

Solution 1,辅助堆栈

费了好大的力气搞明白算法的逻辑了,代码不够简洁,在下一部分继续优化

class Solution(object):
    def decodeString(self, s):
        """
        :type s: str
        :rtype: str
        """
        
        res = ""
        stack = []
        i = 0
        while i < len(s):
            if s[i] == ']':
                alpha = ""
                while stack[-1]!='[':
                    alpha = stack.pop() + alpha
                stack.pop() # 弹出'['
                k = int(stack.pop()) 
                # 将字符串重复k次
                alpha_k_times = ""
                for j in range(0,k): # Note(1)
                    alpha_k_times = alpha_k_times + alpha # Note(2)
                if stack:
                    # 堆栈非空,说明还有'['没有弹出
                    stack.append(alpha_k_times)
                else:
                    # 堆栈空,更新res
                    res = res + alpha_k_times

                i = i+1

            elif s[i].isalpha():
                # s[i]是字母,分成两种情况讨论
                if stack:
                    # case 1: 堆栈非空,说明还有表达式没有计算结束
                    stack.append(s[i])
                else:
                    # case 2: 堆栈空,说明该字符不需要重复,直接更新到res中
                    res = res + s[i]

                i = i+1

            elif s[i].isdigit():
                # s[i]是数字,注意数字不只是1位,解析数字后push到堆栈
                num = 0
                while s[i].isdigit():
                    num = num*10 + int(s[i])
                    i = i+1
                stack.append(num)          
            else:
                # s[i]=='['
                stack.append(s[i])
                i = i+1
        return res

Solution 2:辅助堆栈,简洁的代码

上面的思路整理起来很难了,然而看了大佬的代码之后,大佬的代码能让代码更加简洁
Note(1)的小小改动,字符串可以做乘法,没有必要循环累加了

alhpa_multi_times = k * alpha

Solution 3:让代码更简洁的是更清晰的逻辑和更巧妙的设计

Solution1的求解思路是将’['和数字和字母单独push到堆栈,更巧妙的设计是将(当前循环次数, 上一次字符串结果)二元组push到堆栈

class Solution(object):
    def decodeString(self, s):
        """
        :type s: str
        :rtype: str
        """
        # Solution 2
        # res -> 最终结果也是字母变量, k -> 次数, stack -> 辅助堆栈
        res, k, stack = "", 0, []
        for c in s:
            # '[' -> (当前次数,上一次结果)入栈后,将次数变量和字母变量清零
            if c == '[':
                stack.append((k, res))
                k, res = 0, ""
            # ']' -> 出栈,(当前次数,上一次结果)累加到res中
            elif c == ']':
                k_cur, res_last = stack.pop()
                res = res_last + k_cur * res
            # 数字,计算到次数变量
            elif '0' <= c <= '9':
                k = k*10 + int(c)
            # 字母,累加到字母变量
            else:
                res = res + c
        return res

参考解题图解:
https://leetcode-cn.com/problems/decode-string/solution/decode-string-fu-zhu-zhan-fa-di-gui-fa-by-jyd/

继续加油吧!

朴素思路

class Solution:
    def decodeString(self, s: str) -> str:
        # Solution 2: 
        i = 0
        stack = []
        while i < len(s):
            # s[i]是数字
            if s[i] >= '0' and s[i] <= '9':
                # 数字可能有多位,一次性放到num累积
                num = 0
                while i < len(s) and s[i] >= '0' and s[i] <= '9':
                    num = num*10 + int(s[i])
                    i += 1
                # 将数字放入num_stack,再把num复原
                stack.append(num)               

            # s[i]是'['
            elif s[i] == '[':
                stack.append(s[i])
                i += 1

            # s[i]是']',出堆栈一直到'['为止
            elif s[i] == ']':
                i += 1
                # 出栈
                a = ""
                while stack[-1] != '[':
                    a = stack.pop() + a
                stack.pop() # 弹出'['
                n = stack.pop()
                tmp = ""
                for j in range(0, n):
                    tmp = tmp + a
                # 把tmp放回到堆栈
                stack.append(tmp)
            
            # s[i]是字母,入栈
            elif s[i] >= 'a' and s[i] <= 'z':
                alpha = ""
                while i<len(s) and s[i] >= 'a' and s[i] <= 'z':
                    alpha = alpha + s[i]
                    i += 1
                stack.append(alpha)
        # 遍历弹出栈
        res = ""
        while stack != []:
            res = stack.pop() + res
        return res
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值