题目描述
给定一个经过编码的字符串,返回它解码后的字符串。
编码规则为: k[encoded_string],表示其中方括号内部的 encoded_string 正好重复 k 次。注意 k 保证为正整数。
你可以认为输入字符串总是有效的;输入字符串中没有额外的空格,且输入的方括号总是符合格式要求的。
此外,你可以认为原始数据不包含数字,所有的数字只表示重复的次数 k ,例如不会出现像 3a 或 2[4] 的输入。
测试用例保证输出的长度不会超过 105。
示例 1:
输入:s = “3[a]2[bc]”
输出:“aaabcbc”
示例 2:
输入:s = “3[a2[c]]”
输出:“accaccacc”
示例 3:
输入:s = “2[abc]3[cd]ef”
输出:“abcabccdcdcdef”
示例 4:
输入:s = “abc3[cd]xyz”
输出:“abccdcdcdxyz”
提示:
- 1 <= s.length <= 30
- s 由小写英文字母、数字和方括号 ‘[]’ 组成
- s 保证是一个 有效 的输入。
- s 中所有整数的取值范围为 [1, 300]
思考
利用栈的先进后出特性处理嵌套的括号结构:遇到右括号时,从栈中弹出最近的左括号及其之间的子串,同时提取前面的数字作为重复次数,将子串按次数重复后重新压入栈中。通过这种方式,从内层到外层逐步解析嵌套结构,最终拼接栈中剩余元素得到结果。
算法过程
- 初始化栈:用于存储字符、数字和括号
- 遍历字符串:
- 若遇到非右括号字符,直接入栈
- 若遇到右括号
]:- 弹出栈顶字符,直到遇到左括号
[,拼接这些字符得到待重复子串t - 弹出左括号
[ - 继续弹出栈顶字符,直到非数字,拼接得到重复次数的字符串
numStr - 将
numStr转换为数字repeatNum,并将子串t重复repeatNum次 - 将重复后的字符串重新压入栈中
- 弹出栈顶字符,直到遇到左括号
- 结果处理:遍历结束后,将栈中所有元素拼接即为解码后的字符串
时空复杂度分析
- 时间复杂度:O(N),其中N是解码后字符串的长度。虽然存在重复拼接操作,但每个字符最终只会被处理一次
- 空间复杂度:O(N),栈的最大空间取决于解码后字符串的长度和嵌套深度
代码
/**
* @param {string} s
* @return {string}
*/
var decodeString = function(s) {
const stack = [];
const n = s.length;
for (let c of s) {
if (c === ']') {
let t = '';
while (stack[stack.length-1] !== '[') {
t = stack.pop() + t;
}
stack.pop(); // [
let numStr = '';
while (!isNaN(stack[stack.length-1])) {
numStr = stack.pop() + numStr;
}
const repeatNum = Number(numStr);
for (let i = 0; i < repeatNum; i++) {
stack.push(t);
}
} else {
stack.push(c);
}
}
return stack.join('');
};
1005

被折叠的 条评论
为什么被折叠?



