LeetCode 394 字符串解码,并对于java的正则表达式进行一点了解

本文介绍了一种使用栈和正则表达式的方法来解码一个字符串,其中包含数字和字符的组合,数字部分会按字符出现的顺序重复相应的次数。作者通过建立数栈和符号栈,以及巧妙地利用正则表达式处理转义字符,实现了字符串的解析和处理。
摘要由CSDN通过智能技术生成

本文不是对正则表达式的规范描述,只是对结合题目对正则表达式的一点使用。无需了解的请跳过本文

1.题目

在这里插入图片描述
思路: 思路:1.建立两个栈:数栈和符号栈。2.扫描,遇到数则进数栈,遇到符号[则入栈,遇到字符串则入符号栈,当遇到]时候,从符号栈中弹出字符串直到[或栈空为止,并从数栈弹出栈顶,组成字符串对应倍数的新字符串,并压入字符栈,直到扫描结束
代码部分:

class Solution {
    public String decodeString(String s) {
        // 思路:建立两个栈:数栈和符号栈。
        // 扫描,遇到数则进数栈
        // 扫描,遇到符号[则入栈,遇到字母则如符号栈,当遇到]时候,从符号栈中弹出字符串直到[或栈空为止,并从数栈弹出栈顶,组成
        // 字符串对应倍数的新字符串,并压入字符栈,直到扫描结束
        LinkedList<String> stackStr = new LinkedList();
        LinkedList<Integer> stackNum = new LinkedList();
        // 对s做处理,否则会出现100[ab]但是只能单个字符1,0,0入数字栈等等诸多意外的情况
        String[] splitStr = s.split("(?<=\\[)(?=\\d|\\D)|(?<=\\])(?=\\d|\\D)|(?<=\\d)(?=\\D)|(?<=\\D)(?=\\])|(?<=\\D)(?=\\d)");
        for (int i = 0; i < splitStr.length; i++) {
            String temp = splitStr[i];
            if (temp.equals("[") || temp.matches("[a-z]+")) {
                stackStr.push(temp);// 字母和左括号
            } else if (temp.equals("]")) {// 右括号
                // 如果为]则弹出字符直到[为止和 数一起做处理
                String createStr = "";
                while (!stackStr.isEmpty() && !stackStr.peek().equals("[")) {
                    createStr = stackStr.pop() + createStr;
                }
         

                 }
                stackStr.pop();// 弹出[
                int b = stackNum.pop();
                String res = ac(createStr, b);
                stackStr.push(res);

            } else {// 数字部分处理
                stackNum.push(Integer.parseInt(temp));
            }
        }
        // 如过栈中有数值,则进行处理拼凑后弹出
        if (!stackNum.isEmpty()) {
            return ac(stackStr.pop(), stackNum.pop());
        } else {
            // 按照顺序弹出所有字符串
            String result = "";
            while (!stackStr.isEmpty()) {
                result = stackStr.pop() + result;
            }
            return result;

        }

    }
	//字符串与数字进行倍数处理
    public String ac(String str, int b) {
        String nstr = "";
        for (int i = 0; i < b; i++) {
            nstr = nstr + str;
        }
        return nstr;

    }
}
接下来重点解释下代码中用到的正则表达式

前提:注意不同语言的正则表达式处理是有区别的

所以各位看到其他语言的符合自己想要功能的正则表达式,请不要随意拷贝,否则很可能出现错误

正则表达式

1.正则表达式中的转义字符

在正则表达式中,.^$[]\等都有特定的含义。如果在正则表达式中想与这些字符本身进行匹配的的,需要在这些元字符前加上\对其进行转义。

  1. (?<=\D)(?=\d) - 匹配非数字( \D )和数字( \d )之间的位置
  2. (?<=\d)(?=\D) - 匹配数字和非数字之间的位置。
  3. 需要转义字符\(有些语言对于转义字符处理和java的不同)
  4. \[表示匹配[符号,同理可得\]

\d和\D的含义

\d数字字符匹配。等效于 [0-9]。
\D非数字字符匹配。等效于[^0-9]
同理可得\[和\]等就是匹配[ ]等符号
(?<=\\[)(?=\\d|\\D)|(?<=\\])(?=\\d|\\D)|(?<=\\d)(?=\\D)|(?<=\\D)(?=\\])|(?<=\\D)(?=\\d)
表达意思分别是:
       1.匹配[到(数字与非数字)之间的位置,即[符号 (?<=\\[)(?=\\d|\\D)
       2.匹配]到(数字与非数字)之间的位置,即]符号 (?<=\\])(?=\\d|\\D)
       3.匹配数字到非数字之间的位置,即获取数字部分: (?<=\\d)(?=\\D)  例如:2[be],需要将2和[拆开
       4.匹配非数字到]之间的位置 ,即获取]之前的字母部分  (?<=\\D)(?=\\]) 例如:[be] ,由于1,可以拆开[符号,由于4,可以拆开be,由于2,可以获取]
       5.匹配非数字到数字的部分         (?<=\\D)(?=\\d) 例如:对于3[a2[be]],这里就有a2,需要拆开a和2 (?<=\\d)(?=\\D)

具体例子:
1.匹配数字,直到遇到非数字
在这里插入图片描述
2.匹配右边部分包括 [ 的内容,直到遇到非数字或数字部分
在这里插入图片描述
3.匹配左边部分包括 ] 的内容,直到遇到非数字或数字部分
在这里插入图片描述
4.左边匹配非数部分,直到遇到]
在这里插入图片描述
5.左边匹配到非数字,直到遇到数字的部分
在这里插入图片描述

对于以上1-5进行或|运算,即满足一个就要拆分

言归正传
题解效率很低,可以进行优化,例如使用StringBuilder等,或者采取官方题解的递归等思路进行
本题目用该方法只是因为想用正则,但是题解的正则基本都是python和JavaScript。
在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值