【做题也是一场游戏】739. 每日温度

222 阅读1分钟

题目地址

leetcode-cn.com/problems/da…

题目描述

请根据每日 气温 列表,重新生成一个列表。对应位置的输出为:要想观测到更高的气温,至少需要等待的天数。如果气温在这之后都不会升高,请在该位置用 0 来代替。

例如,给定一个列表 temperatures = [73, 74, 75, 71, 69, 72, 76, 73],你的输出应该是 [1, 1, 4, 2, 1, 1, 0, 0]

提示: 气温 列表长度的范围是 [1, 30000]。每个气温的值的均为华氏度,都是在 [30, 100] 范围内的整数。

题解

记录第一次出现的位置

  • 构建一个存储每个温度第一次出现的位置
  • 从后往前遍历,每遍历一个温度,就记录该温度第一次出现的位置
  • T+1 开始到 100 找,这个区间的温度是否出现过,第一个出现温度的索引减去当前索引就是答案
class Solution {
    public int[] dailyTemperatures(int[] T) {
        int length = T.length;
        int[] ans = new int[length];
        int[] next = new int[101];
        Arrays.fill(next, Integer.MAX_VALUE);
        for (int i = length - 1; i >= 0; --i) {
            int warmerIndex = Integer.MAX_VALUE;
            for (int t = T[i] + 1; t <= 100; ++t) {
                if (next[t] < warmerIndex) {
                    warmerIndex = next[t];
                }
            }
            if (warmerIndex < Integer.MAX_VALUE) {
                ans[i] = warmerIndex - i;
            }
            next[T[i]] = i;
        }
        return ans;
    }
}

复杂度分析

  • 时间复杂度:O(nm)O(nm),其中 nn 是温度列表的长度,mm 是数组 next 的长度,在本题中温度不超过 100100,所以 mm 的值为 100100。反向遍历温度列表一遍,对于温度列表中的每个值,都要遍历数组 next 一遍。

  • 空间复杂度:O(m)O(m),其中 mm 是数组 next 的长度。除了返回值以外,需要维护长度为 mm 的数组 next 记录每个温度第一次出现的下标位置。

单调栈

前面的方法是从后遍历,那么从前往后遍历怎么办呢?

从前往后遍历,还希望复杂度为 O(n)O(n), 那么我们只能遍历一遍

对于 ii, 找到一个 jj, 使得 T[i]<T[j]T[i] < T[j], 如果关注 ii,那么就需要往后遍历找到 jj, 这样复杂度是 O(n2)O(n^2)。如果关注 jj, 那么就是 jj 之前的位置, 有哪些比 jj 对应温度小的,这样只需要遍历一遍就行

class Solution {
    public int[] dailyTemperatures(int[] T) {
        int length = T.length;
        int[] ans = new int[length];
        Deque<Integer> stack = new LinkedList<Integer>();
        for (int i = 0; i < length; i++) {
            int temperature = T[i];
            while (!stack.isEmpty() && temperature > T[stack.peek()]) {
                int prevIndex = stack.pop();
                ans[prevIndex] = i - prevIndex;
            }
            stack.push(i);
        }
        return ans;
    }
}

复杂度分析

  • 时间复杂度:O(n)O(n),其中 nn 是温度列表的长度。正向遍历温度列表一遍,对于温度列表中的每个下标,最多有一次进栈和出栈的操作。

  • 空间复杂度:O(n)O(n),其中 nn 是温度列表的长度。需要维护一个单调栈存储温度列表中的下标。