力扣739,496,503(单调栈)

739.每日温度

基本思想:

1.单调栈里存放的元素是什么?

单调栈里只需要存放元素的下标i就可以了,如果需要使用对应的元素,直接T[i]就可以获取。

2.单调栈里元素是递增还是递减?

顺序为栈头到栈底

此题使用递增序列,只有递增的时候,加入一个元素i,

才知道栈顶元素在数组中右面第一个比栈顶元素大的元素是i。

具体实现:

 

 

代码:

class Solution {
    public int[] dailyTemperatures(int[] temperatures) {
        Stack<Integer> stack = new Stack<>();
        int[] res = new int[temperatures.length];
        for (int i = 0; i < temperatures.length; i++) {
            while (!stack.isEmpty() && temperatures[i] > temperatures[stack.peek()]) {
                int preIndex = stack.pop();
                res[preIndex] = i - preIndex;
            }
            stack.push(i);
        }
        return res;
    }
}

 

496.下一个更大元素

基本思想:

单调栈

具体实现:

1.result数组如果某位置没有被赋值,就应该是是-1,所以result数组初始化为-1。

2.在遍历nums2的过程中,要判断nums2[i]是否在nums1中出现过,

因为最后是要根据nums1元素的下标来更新result数组。

3.题目中说是两个没有重复元素 的数组 nums1 和 nums2

用map来做映射了。根据数值快速找到下标,

还可以判断nums2[i]是否在nums1中出现过。

综上

        Stack<Integer> temp = new Stack<>();
        int[] res = new int[nums1.length];
        Arrays.fill(res,-1);
        HashMap<Integer, Integer> hashMap = new HashMap<>();
        for (int i = 0 ; i< nums1.length ; i++){
            hashMap.put(nums1[i],i);
        }

 

4.分析三种情况

(情况1)当前遍历的元素T[i]小于栈顶元素T[st.top()]的情况

                此时满足递增栈(栈头到栈底的顺序),所以直接入栈。

(情况2)当前遍历的元素T[i]等于栈顶元素T[st.top()]的情况

                如果相等的话,依然直接入栈,因为要求的是右边第一个比自己大的元素,而不是大于等于

(情况3)当前遍历的元素T[i]大于栈顶元素T[st.top()]的情况

                 此时如果入栈就不满足递增栈了,这也是找到右边第一个比自己大的元素的时候。

 

 

代码:

class Solution {
    public int[] nextGreaterElement(int[] nums1, int[] nums2) {
        Stack<Integer> temp = new Stack<>();
        int[] res = new int[nums1.length];
        Arrays.fill(res,-1);
        HashMap<Integer,Integer> hashMap = new HashMap<>();
        for (int i = 0; i < nums1.length; i++) {
            hashMap.put(nums1[i],i);
        }
        temp.add(0);
        for (int i = 1; i < nums2.length; i++) {
            if (nums2[i] <= nums2[temp.peek()]) {
                temp.add(i);
            } else {
                while (!temp.isEmpty() && nums2[temp.peek()] < nums2[i]){
                    if (hashMap.containsKey(nums2[temp.peek()])){
                        Integer index = hashMap.get(nums2[temp.peek()]);
                        res[index] = nums2[i];
                    }
                    temp.pop();
                }
                temp.add(i);
            }
        }
        return res;
    }
}

 

503.下一个更大元素II

基本思想:

在遍历的过程中模拟走了两遍nums

具体实现:

[1,2,1] 长度为3,遍历时i范围为0-5(2*length)

i%length

(0,1,2,3,4,5)%3 = (0,1,2,0,1,2)

代码:

class Solution {
    public int[] nextGreaterElements(int[] nums) {
        if(nums == null || nums.length <= 1) {
            return new int[]{-1};
        }
        int size = nums.length;
        int[] result = new int[size];
        Arrays.fill(result,-1);
        Stack<Integer> st = new Stack<>();
        for(int i = 0; i < 2*size; i++){
            while(!st.empty() && nums[i % size] > nums[st.peek()]){
                result[st.peek()] = nums[i % size];
                st.pop();
            }
            st.push(i  % size);
        }
        return result;
    }
}

 

 

 

 

posted @ 2021-12-30 21:26  最近饭吃的很多  阅读(35)  评论(0编辑  收藏  举报