22、括号生成
0. 题面
数字 n 代表生成括号的对数,请你设计一个函数,用于能够生成所有可能的并且有效的括号组合。
示例 1:
输入:n = 3
输出:["((()))","(()())","(())()","()(())","()()()"]
示例 2:
输入:n = 1
输出:["()"]
提示: ● 1 <= n <= 8
解法
var generateParenthesis = function (n) {
const result = [];
const dfs = (lRemain, rRemain, str) => {
// 左右括号所剩的数量,str是当前构建的字符串
if (str.length === 2 * n) {
// 字符串构建完成
result.push(str); // 加入解集
return; // 结束当前递归分支
}
if (lRemain > 0) {
// 只要左括号有剩,就可以选它,然后继续做选择(递归)
dfs(lRemain - 1, rRemain, str + '(');
}
if (lRemain < rRemain) {
// 右括号比左括号剩的多,才能选右括号
dfs(lRemain, rRemain - 1, str + ')'); // 然后继续做选择(递归)
}
};
dfs(n, n, ''); // 递归的入口,剩余数量都是n,初始字符串是空串
return result;
};
思路:
- 递归函数
dfs的参数是左括号和右括号的剩余数量,以及当前构建的字符串。 - 当字符串构建完成时,即
str.length === 2 * n时,加入解集。 - 选择左括号时,只要
lRemain > 0,就可以选它,然后继续做选择(递归)。 - 选择右括号时,只要
lRemain < rRemain,才能选右括号,然后继续做选择(递归)。 - 递归的入口是
dfs(n, n, ''),剩余数量都是n,初始字符串是空串。
739、每日温度
0. 题面
给定一个整数数组 temperatures ,表示每天的温度,返回一个数组 answer ,其中 answer[i] 是指对于第 i 天,下一个更高温度出现在几天后。如果气温在这之后都不会升高,请在该位置用 0 来代替。
示例 1:
输入: temperatures = [73, 74, 75, 71, 69, 72, 76, 73];
输出: [1, 1, 4, 2, 1, 1, 0, 0];
示例 2:
输入: temperatures = [30, 40, 50, 60];
输出: [1, 1, 1, 0];
示例 3:
输入: temperatures = [30, 60, 90];
输出: [1, 1, 0];
提示:
1. 1 <= temperatures.length <= 10^5
2. 30 <= temperatures[i] <= 100
解法 1
var dailyTemperatures = function (temperatures) {
const len = temperatures.length;
const answer = new Array(len);
for (let i = 0; i < len - 1; i++) {
const element = temperatures[i];
const greaterIndex = temperatures.findIndex((item, index) => item > element && index > i);
answer[i] = greaterIndex === -1 ? 0 : greaterIndex - i;
}
answer[len - 1] = 0;
return answer;
};
思路:
- 遍历数组,对于每个元素,查找后面第一个比它大的元素的下标,如果找不到则为 0
- 时间复杂度 O(n^2),空间复杂度 O(n)
解法 2
var dailyTemperatures = function (temperatures) {
const len = temperatures.length;
const answer = new Array(len).fill(0);
const stack = [];
for (let i = len - 1; i >= 0; i--) {
while (stack.length && temperatures[i] >= temperatures[stack[stack.length - 1]]) {
stack.pop();
}
if (stack.length) {
answer[i] = stack[stack.length - 1] - i;
}
stack.push(i);
}
return answer;
};
- 优化:可以使用单调栈来优化,
- 从后往前遍历,维护一个单调递减栈,栈中存放的是下标
- 如果栈为空,则直接入栈
- 如果栈不为空,且当前元素大于栈顶元素,则出栈,计算出栈顶元素到当前元素的距离,将结果保存到结果数组中
- 如果栈不为空,且当前元素小于等于栈顶元素,则入栈
- 遍历结束后,栈中剩余的元素对应的结果都为 0
- 时间复杂度 O(n),空间复杂度 O(n)