LeetCode_String_394. 字符串解码 Decode String【字符串,递归】【java】【中等】

目录

一,题目描述

英文描述

中文描述

示例与说明

二,解题思路

三,AC代码

Java

四,解题过程

第一博

第二搏


一,题目描述

英文描述

Given an encoded string, return its decoded string.

The encoding rule is: k[encoded_string], where the encoded_string inside the square brackets is being repeated exactly k times. Note that k is guaranteed to be a positive integer.

You may assume that the input string is always valid; No extra white spaces, square brackets are well-formed, etc.

Furthermore, you may assume that the original data does not contain any digits and that digits are only for those repeat numbers, k. For example, there won't be input like 3a or 2[4].

中文描述

给定一个经过编码的字符串,返回它解码后的字符串。

编码规则为: k[encoded_string],表示其中方括号内部的 encoded_string 正好重复 k 次。注意 k 保证为正整数。

你可以认为输入字符串总是有效的;输入字符串中没有额外的空格,且输入的方括号总是符合格式要求的。

此外,你可以认为原始数据不包含数字,所有的数字只表示重复的次数 k ,例如不会出现像 3a 或 2[4] 的输入。

示例与说明

来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/decode-string
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

二,解题思路

核心问题:寻找匹配的左右括号(找到与最左侧括号相匹配的右括号,即可对中间的字符串递归调用算法)。

  • 由于括号可能是并列([][][])也可能是嵌套([[[]]]),所以需要记录左括号数目level。若字符为 '[' 则level++,若为 ']' 则level--(表示抵消了一个左括号);
  • 当level为0时,即找到了匹配的左右括号;

主要问题解决了,细节就慢慢调试吧╮(╯▽╰)╭

三,AC代码

Java

class Solution {
    public String decodeString(String s) {
        StringBuilder repeat = new StringBuilder();     // 存放需要重复的次数
        StringBuilder content = new StringBuilder();    // 存放原始数据(不包含数字)
        StringBuilder ans = new StringBuilder();        // 存放结果
        int start = -1, level = 0;                      // start: 第一个左括号的位置, level: 左括号数目
        int len = s.length();
        for (int i = 0; i < len; i++) {
            char c = s.charAt(i);
            // 当左括号数目为0时
            if (level == 0) {
                if (c == '[') {
                    if (level == 0) {
                        start = i;                      // 记录第一个左括号的位置
                    }
                    level++;// 左括号数目加一
                } else if (c >= '0' && c <= '9') {
                    // 当数字之前存在字符时,将content中存放的数据添加到结果中
                    if (content.length() != 0) {
                        ans.append(content.toString());
                        content.setLength(0);
                    }
                    repeat.append(c);
                } else {
                    content.append(c);
                }
            } 
            // 当左括号数目不为0时
            else {
                if (c == '[') {
                    level++;                            // 左括号数目加一
                } else if (c == ']') {
                    level--;                            // 左括号数目减一
                    // 找到与第一个左括号匹配的右括号位置
                    if (level == 0) {
                        // 递归获得左右括号内字符串处理后的结果
                        String s1 = decodeString(s.substring(start + 1, i));
                        int num = Integer.valueOf(repeat.toString());
                        for (int j = 0; j < num; j++) {
                            ans.append(s1);
                        }
                        repeat.setLength(0);            // 将之前记录的重复数字设置为0
                    }
                }
            }
        }
        // 处理字符串中不含括号的情况,比如"abc"
        if (content.length() != 0) {
            ans.append(content.toString());
        }
        return ans.toString();
    }
}

四,解题过程

第一博

一开始以为挺轻松的。。。结果还是没搞清楚递归的流程。写到一半写不下去了,发现算法完全是错的

class Solution {
    public String decodeString(String s) {
        boolean flag = false;// 未发现'['时为false
        int start = -1, end = -1;
        StringBuilder repeat = new StringBuilder();
        StringBuilder content = new StringBuilder();
        StringBuilder ans = new StringBuilder();
        
        for (int i = 0; i < s.length(); i++) {
            char c = s.charAt(i);
            if (c == '[') {
                start = i;
                continue;
            } else if (c == ']') {
                end = i;
                String s1 = decodeString(s.substring(start + 1, end));
                start = -1;
                end = -1;
                System.out.println(repeat.toString());
                int num = Integer.valueOf(repeat.toString());
                for (int j = 0; j < num; j++) {
                    ans.append(s1);
                }
                repeat.setLength(0);
                content.setLength(0);
            } else if (c >= '0' && c <= '9') {
                if (content.length() != 0) {
                    ans.append(content.toString());
                    content.setLength(0);
                }
                repeat.append(c);
            } else {
                content.append(c);
            }
        }
        ans.append(content.toString());
        return ans.toString();
    }
}

第二搏

重新调整思路,将重心放在寻找子问题上。

发现关键:左右括号(找到与最左侧括号相匹配的右括号,即可对中间的字符串递归调用算法)。

  • 由于括号可能是并列([][][])也可能是嵌套([[[]]]),所以需要记录左括号数目level。若字符为 '[' 则level++,若为 ']' 则level--(表示抵消了一个左括号);
  • 当level为0时,即找到了匹配的左右括号;

猜你喜欢

转载自blog.csdn.net/qq_41528502/article/details/121586145