Leetcode 915. 分割陣列
阿新 • • 發佈:2019-01-09
即使自己做了幾遍,還是沒有真正的開竅,領會精髓。第一眼看上去,這是一道陣列分割的題目。
給定一個數組
A
,將其劃分為兩個不相交(沒有公共元素)的連續子陣列left
和right
, 使得:
left
中的每個元素都小於或等於right
中的每個元素。left
和right
都是非空的。left
要儘可能小
思路一:那麼是按索引位置先分割,然後用暴力法比較?很容易得到O(n^3)解決方案(AC)
leetcode對時間複雜度的要求就是如此苛刻。
顯然這個是糟糕的實踐。class Solution { public int partitionDisjoint(int[] A) { for(int i=1; i < A.length; i++){ int flag = 0; for(int j=0; j < i; j++){ for(int k=i;k<A.length;k++){ if (A[j] > A[k]) flag=1; break; } if(flag == 1) break; } if (flag==0) return i; } return 0; } }
思路二:提煉維度。這裡說的維度,是在陣列迭代過程中產生的,也是貪心演算法的概念。比如你在沙灘上散步,背後留下的是你之前走過的腳印,每個腳印都是獨一無二的,輪廓是一樣的,但是腳印的力度、深淺、相對位置等因素不盡相同。 當然,如果有必要你可以拿一把尺子、一支筆、一張紙,當你每踩下一步,都能以資料的形式把每一步給量化。
維度只有在集合中才能體現出來。單一的個體不存在大和小,高和低這種概念。在陣列中,通過線性迭代會產生集合的維度,這種維度在迭代的過程中也是一直變化的。
回到Leetcode題目本身,
left
中的每個元素都小於或等於right
中的每個元素。顯然,left和right各是一個集合,而這裡需要考慮left中最大值(leftMax)和right中最小值(rightMin)這2個維度,只有當滿足leftMax <= rightMin的時候就能得到答案。class Solution { public int partitionDisjoint(int[] A) { int leftMax = A[0], rightMin = A[0], index=0; for(int i=0;i<A.length;i++){ if(A[i] < rightMin){ rightMin=leftMax; index=i; } leftMax=Math.max(leftMax, A[i]); } return index+1; } }