ETH官方钱包

前往
大廳
主題

LeetCode - 0845. Longest Mountain in Array

Not In My Back Yard | 2023-11-09 12:00:01 | 巴幣 0 | 人氣 98

題目連結:


題目意譯:你可能可以憶起一個陣列 arr 是一個山陣列(Mountain Array)若且唯若:
arr.length ≧ 3
存在某索引值 i(索引值從 0 開始)有著 0 < i < arr.length - 1 並使得:
    arr[0] < arr[1] < ... < arr[i - 1] < arr[i]
    arr[i] > arr[i + 1] > ... > arr[arr.length - 1]

給定一整數陣列 arr,回傳那些是山陣列中的子陣列中最長之長度。如果沒有任何子陣列是山陣列,則回傳 0。

限制:
1 ≦ arr.length ≦ 10 ^ 4
0 ≦ arr[i] ≦ 10 ^ 4

進階:
你可以只掃過一次(One Pass)便求得解嗎?
你可以只使用 O(1)(額外)空間便求得解嗎?



範例測資:
範例 1:
輸入: arr = [2,1,4,7,3,2,5]
輸出: 5
解釋: 最大的山為 [1,4,7,3,2],其長度為 5。

範例 2:
輸入: arr = [2,2,2]
輸出: 0
解釋: 裡面沒有山。


解題思維:
解法的精神有點類似於這題中間提及的方式。也就是記錄前一刻以及現在的上升下降之情形(以及這些片段的長度)。為此我們需要三個變數 M 、 I 、 D,分別用來記錄「答案」、「目前看到的遞增片段之長度」、「目前看到的遞減片段之長度」。後面兩者分別是用來記錄一座山的「左側」(遞增片段)以及「右側」(遞減片段)。

因此當掃過 arr 時,對於每個 arr[i](i > 0)去判斷 arr[i - 1] 與 arr[i] 的大小關係:
    如果 arr[i - 1] > arr[i],也就是說現在是「遞減」片段,因此以 arr[i - 1] 作為結尾的最長的山(如果存在的話)可以繼續延伸到 arr[i],因此先前的 I 保持不變、D 則增加 1。

    如果 arr[i - 1] == arr[i],也就是說以 arr[i - 1] 作為結尾的最長的山(如果存在的話)無法繼續延伸。因此我們可以判斷該座山是不是真的是一座山,也就是要判斷先前的 I 、 D 之值是否滿足 I > 0 、 D > 0 以及 I + D > 1。如果都滿足則才是題目所求的山,因此可以跟「先前」找到的答案去比較取最大值作為新的 M 值即可。最後因為這可能是一個新的山之開始處,因此需要將 I 和 D 歸零。

    如果 arr[i - 1] < arr[i],也就是說現在是「遞增」片段。而這有可能是如上一個情境同樣是以 arr[i - 1] 作為結尾的山無法繼續延伸之情況,此時代表先前的 D 值並不為 0(代表先前已經經歷過「遞減」),因此需要判斷山的合法性並長度的計算,並且記得將 I 和 D 之值歸零。最後因為這邊是「遞增」片段,因此不論先前情況如何,最後都需將 I 加 1。

最後因為掃完之後最後一座山(如果真的是山的話)將不會被判斷到,因此要做與其他山一樣的判斷以及計算。最後得到的 M 值即為所有山的長度最大值。




此次分享到此為止,如有任何更加簡潔的想法或是有說明不清楚之地方,也煩請各位大大撥冗討論。

創作回應

追蹤 創作集

作者相關創作

更多創作