【栈】B032_LC_132模式(暴力双指针 / 单调递减栈)

给定一个整数序列:a1, a2, …, an,一个132模式的子序列 ai, aj, ak 被定义为:当 i < j < k 时,ai < ak < aj。设计一个算法,当给定有 n 个数字的序列时,验证这个序列中是否含有132模式的子序列。

注意:n 的值小于15000

示例1:
输入: [1, 2, 3, 4]
输出: False
解释: 序列中不存在132模式的子序列。

示例 2:
输入: [3, 1, 4, 2]
输出: True
解释: 序列中有 1 个132模式的子序列: [1, 4, 2].

示例 3:
输入: [-1, 3, 2, 0]
输出: True
解释: 序列中有 3 个132模式的的子序列: [-1, 3, 2], [-1, 3, 0] 和 [-1, 2, 0].
方法一:山脉思想+双指针

思路

借鉴山脉的思想,当找到一个上坡 A[i…k] 时,如果有 132 模式则区间 [k, n) 必定有一个下坡:下坡 [k, n) 中的数字都大于 min_element(A[i…k]) 且小于 A[k]

1996ms…算法最坏情况下会被卡成 O ( n 2 ) O(n^2) O(n2)

class Solution {
public:
    bool find132pattern(vector<int>& A) {
    	int n=A.size();
    	if (n<3) return false;

    	int mi=A[0], i=1;
        while (i<n) {
            mi=min(mi, A[i]); //若mi...A[i]是上坡,则A[i]必定是最大的
            if (mi != A[i]) for (int j=i+1; j<n; j++) if (A[j]<A[i] && A[j]>mi) {
                return true;
            }
            i++;
        }
		return false;    	
    }
};

复杂度分析

  • Time O ( n Q ) O(nQ) O(nQ)
  • Space O ( 1 ) O(1) O(1)

方法二:单调栈

参考别人的思路,利用最小前缀数组 mi +单调递减栈;(min[i] 表示子数组 A[0…i] 中的最小值)

  • 对于一个上坡 A[i…j],在下坡 A[j+1, n) 中找一个比上坡中最小数还要大的数 tar
  • tar 可以像方法一那样用 O(n) 循环找, 也可以从后往前遍历 i,维护一个单调递减栈:栈中元素都是大于 min[i] 且小于 A[i] 的,只要有这样的元素就返回 true
class Solution {
public:
    bool find132pattern(vector<int>& A) {
    	int n=A.size();
    	if (n<3) return false;

    	int mi[n]; memset(mi, 0, sizeof mi); mi[0]=A[0]; 
    	for (int i=1; i<n; i++) mi[i]=min(mi[i-1], A[i]);

    	stack<int> st;
    	for (int i=n-1; i>0; i--) if (A[i]>mi[i]) {
    		while (!st.empty() && st.top()<=mi[i]) st.pop();
    		if (!st.empty() && st.top()<A[i]) return true;
    		st.push(A[i]);
    	}
		return false;    	
    }
};

复杂度分析

  • Time O ( n ) O(n) O(n)
  • Space O ( n ) O(n) O(n)
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值