1. 程式人生 > 其它 >2022-4-20 二分查詢

2022-4-20 二分查詢

354. 俄羅斯套娃信封問題

給你一個二維整數陣列 envelopes ,其中 envelopes[i] = [wi, hi] ,表示第 i 個信封的寬度和高度。

當另一個信封的寬度和高度都比這個信封大的時候,這個信封就可以放進另一個信封裡,如同俄羅斯套娃一樣。

請計算 最多能有多少個 信封能組成一組“俄羅斯套娃”信封(即可以把一個信封放到另一個信封裡面)。

注意:不允許旋轉信封。

 1 class Solution {
 2     public int maxEnvelopes(int[][] envelopes) {
 3         PriorityQueue<int
[]> queue=new PriorityQueue<>( 4 new Comparator<int[]>(){ 5 @Override 6 public int compare(int[] a,int[] b){ 7 if (a[0]!=b[0]) return a[0]-b[0]; 8 else return b[1]-a[1]; 9 } 10 }
11 ); 12 for (int[] x:envelopes){ 13 queue.offer(x); 14 } 15 int n=envelopes.length; 16 int[] h=new int[n]; 17 int index=0; 18 while (!queue.isEmpty()) { 19 h[index]=queue.poll()[1]; 20 index++; 21 } 22
int piles=0; 23 int[] dp=new int[n]; 24 for (int i=0;i<n;i++){ 25 int pair=h[i]; 26 int left=0,right=piles; 27 while (left<right) { 28 int mid=(left+right)/2; 29 if (dp[mid]>=pair){ 30 right=mid; 31 }else{ 32 left=mid+1; 33 } 34 } 35 if (left==piles) piles++; 36 dp[left]=h[i]; 37 } 38 39 return piles; 40 } 41 }

思路:二維最長遞增子序列可以通過優先排列的順序轉化為一維。方法為先按照第一個寬度從小到大排序,相同就按照高度從大到小排列。

轉化為高度的最長遞增子序列後,可以動態規劃。

也可以利用耐心排序的方法。紙牌遊戲 二分實現。

小的可以壓在大的牌上面,否則開一個新的牌堆。

利用二分查詢當前的牌放在哪裡,或者新開牌堆。

最長的序列就是牌堆的數量。