1. 程式人生 > >LeetCode962. 最大寬度坡

LeetCode962. 最大寬度坡

問題:最大寬度坡

給定一個整數陣列 A是元組 (i, j),其中  i < j 且 A[i] <= A[j]。這樣的坡的寬度為 j - i

找出 A 中的坡的最大寬度,如果不存在,返回 0 。

 

示例 1:

輸入:[6,0,8,2,1,5]
輸出:4
解釋:
最大寬度的坡為 (i, j) = (1, 5): A[1] = 0 且 A[5] = 5.

示例 2:

輸入:[9,8,1,0,1,9,4,0,4,1]
輸出:7
解釋:
最大寬度的坡為 (i, j) = (2, 9): A[2] = 1 且 A[9] = 1.

 

提示:

  1. 2 <= A.length <= 50000
  2. 0 <= A[i] <= 50000

 

連結:https://leetcode-cn.com/contest/weekly-contest-116/problems/maximum-width-ramp/

分析:

問題不難,早早的就有了思路 ,可惜一直卡在50000陣列超時上 ,好在不斷優化(或者Server突然效能給力?)最後十來分鐘AC了。

想要找到最大的j-i,滿足i<j且A[i]<=A[j]。

基本思路就是二重迴圈,但是要做一些優化。

1.如果找到了一組符合要求的n1,n2,那麼對於後續的m1>n1,其下限m2必須大於n2,才有可能m2-m1>n2-n1(m1>n1) [通過數軸會更直觀一些]

2.如果已經有了符合要求的n1,n2,那麼對於n11>n1,如果A[n11]>=A[n1],則沒必要看,其結果必定小於n1, 比如下標i1,i2,i3依次遞增,如果A[i1]<=A[i2],A[i2]<=A[i3],那麼A[i1]<=A[i3],i3-i1>i3-i2

3.在第二層迴圈的時候, 不但對下限有要求,而且m2-m1要大於已知的最大寬度。

AC Code:

 

class Solution {
public:
int maxWidthRamp(vector<int>& A) {
        int
ret = 0; int rightlimit = 0; int predata = -1; for (unsigned int i = 0; i < A.size(); i++) { if (predata == -1) { predata = A[i]; } else { if (predata > A[i]) { predata = A[i]; } else { continue; } } if (A.size() - 1 - i < ret) { return ret; } for (unsigned int j = A.size()-1; j > rightlimit && j-i>ret; j--) { steps++; if (A[j] >= A[i]) { if (j - i > ret) { ret = j - i; } rightlimit = j; break; } } } return ret; } };

雖然AC了,完賽後檢視通過時間,98個測例,用時1880ms,還有很大的優化空間。

其他:

1.第一code:

class Solution:
    def maxWidthRamp(self, A):
        """
        :type A: List[int]
        :rtype: int
        """
        l = []
        for i in range(len(A)):
            l.append((A[i], i))
        l.sort()
        res = 0
        small = l[0][1]
        for _,e in l:
            if e < small:
                small = e
            else:
                if e - small > res:
                    res = e - small
        return res

剛注意到國內和國外排行榜是分離的,國際版第一code:

#include<stdio.h>
#include<iostream>
#include<vector>
#include<algorithm>
#include<string>
#include<string.h>
using namespace std;

typedef long long LL;
typedef vector<int> VI;

#define REP(i,n) for(int i=0, i##_len=(n); i<i##_len; ++i)
#define EACH(i,c) for(__typeof((c).begin()) i=(c).begin(),i##_end=(c).end();i!=i##_end;++i)
#define eprintf(...) fprintf(stderr, __VA_ARGS__)

template<class T> inline void amin(T &x, const T &y) { if (y<x) x=y; }
template<class T> inline void amax(T &x, const T &y) { if (x<y) x=y; }
template<class Iter> void rprintf(const char *fmt, Iter begin, Iter end) {
    for (bool sp=0; begin!=end; ++begin) { if (sp) putchar(' '); else sp = true; printf(fmt, *begin); }
    putchar('\n');
}
class Solution {
public:
    int maxWidthRamp(vector<int>& A) {
    vector<pair<int, int> > t;
    REP (i, A.size()) t.emplace_back(A[i], i);
    sort(t.begin(), t.end());
    int ans = 0;
    int left = t[0].second;
    for (int i=1; i<(int)t.size(); i++) {
        amax(ans, t[i].second - left);
        amin(left, t[i].second);
    }
        
    return ans;
    }
};