中文亚洲精品无码_熟女乱子伦免费_人人超碰人人爱国产_亚洲熟妇女综合网

當前位置: 首頁 > news >正文

網站域名登陸長沙seo優(yōu)化價格

網站域名登陸,長沙seo優(yōu)化價格,帶地板翻轉的網站怎么做,wordpress 如何漢化主題文章目錄 題目標題和出處難度題目描述要求示例數據范圍 解法一思路和算法代碼復雜度分析 解法二思路和算法代碼復雜度分析 題目 標題和出處 標題:尋找兩個正序數組的中位數 出處:4. 尋找兩個正序數組的中位數 難度 8 級 題目描述 要求 給定兩個大…

文章目錄

  • 題目
    • 標題和出處
    • 難度
    • 題目描述
      • 要求
      • 示例
      • 數據范圍
  • 解法一
    • 思路和算法
    • 代碼
    • 復雜度分析
  • 解法二
    • 思路和算法
    • 代碼
    • 復雜度分析

題目

標題和出處

標題:尋找兩個正序數組的中位數

出處:4. 尋找兩個正序數組的中位數

難度

8 級

題目描述

要求

給定兩個大小分別為 m \texttt{m} m n \texttt{n} n 的升序數組 nums1 \texttt{nums1} nums1 nums2 \texttt{nums2} nums2,返回這兩個升序數組的中位數。

要求時間復雜度是 O(log (m + n)) \texttt{O(log (m + n))} O(log?(m?+?n))

示例

示例 1:

輸入: nums1 = [1,3], nums2 = [2] \texttt{nums1 = [1,3], nums2 = [2]} nums1?=?[1,3],?nums2?=?[2]
輸出: 2.00000 \texttt{2.00000} 2.00000
解釋:合并數組是 [1,2,3] \texttt{[1,2,3]} [1,2,3],中位數是 2 \texttt{2} 2

示例 2:

輸入: nums1 = [1,2], nums2 = [3,4] \texttt{nums1 = [1,2], nums2 = [3,4]} nums1?=?[1,2],?nums2?=?[3,4]
輸出: 2.50000 \texttt{2.50000} 2.50000
解釋:合并數組是 [1,2,3,4] \texttt{[1,2,3,4]} [1,2,3,4],中位數是 2 + 3 2 = 2.5 \dfrac{\texttt{2} + \texttt{3}}{\texttt{2}} = \texttt{2.5} 22+3?=2.5。

數據范圍

  • nums1.length = m \texttt{nums1.length} = \texttt{m} nums1.length=m
  • nums2.length = n \texttt{nums2.length} = \texttt{n} nums2.length=n
  • 0 ≤ m ≤ 1000 \texttt{0} \le \texttt{m} \le \texttt{1000} 0m1000
  • 0 ≤ n ≤ 1000 \texttt{0} \le \texttt{n} \le \texttt{1000} 0n1000
  • 1 ≤ m + n ≤ 2000 \texttt{1} \le \texttt{m} + \texttt{n} \le \texttt{2000} 1m+n2000
  • -10 6 ≤ nums1[i], nums2[i] ≤ 10 6 \texttt{-10}^\texttt{6} \le \texttt{nums1[i], nums2[i]} \le \texttt{10}^\texttt{6} -106nums1[i],?nums2[i]106

解法一

思路和算法

已知兩個升序數組的長度分別是 m m m n n n。計算兩個升序數組的中位數可以轉換成找到兩個升序數組的所有元素中的第 k k k 小元素,其中 0 ≤ k < m + n 0 \le k < m + n 0k<m+n。用 total = m + n \textit{total} = m + n total=m+n 表示兩個升序數組的長度之和。當 total \textit{total} total 是奇數時, k = total ? 1 2 k = \dfrac{\textit{total} - 1}{2} k=2total?1?,第 k k k 小元素即為中位數;當 total \textit{total} total 是偶數時,分別取 k = total 2 ? 1 k = \dfrac{\textit{total}}{2} - 1 k=2total??1 k = total 2 k = \dfrac{\textit{total}}{2} k=2total?,兩次第 k k k 小元素的平均數即為中位數。因此,根據兩個升序數組的長度之和是奇數或偶數,執(zhí)行一次或兩次尋找第 k k k 小元素的操作,即可得到中位數。

由于題目要求時間復雜度是 O ( log ? ( m + n ) ) O(\log (m + n)) O(log(m+n)),因此要求每次尋找第 k k k 小元素的操作的時間復雜度是 O ( log ? ( m + n ) ) O(\log (m + n)) O(log(m+n))。需要使用二分查找實現。

k k k 表示目標值在剩余元素中的序號( k k k 0 0 0 開始,序號為 k k k 表示剩余元素中有 k k k 個元素小于等于目標值),用 index 1 \textit{index}_1 index1? index 2 \textit{index}_2 index2? 分別表示數組 nums 1 \textit{nums}_1 nums1? nums 2 \textit{nums}_2 nums2? 的首個剩余元素的下標,初始時 index 1 \textit{index}_1 index1? index 2 \textit{index}_2 index2? 都等于 0 0 0。剩余元素表示可能是目標值的元素,查找過程中將不可能是目標值的元素排除。

每次查找時,分別考慮兩個數組的剩余元素中最小的 ? k 2 ? \Big\lceil \dfrac{k}{2} \Big\rceil ?2k?? 個元素,共考慮 k + 1 k + 1 k+1 個元素(當 k k k 是奇數時)或 k k k 個元素(當 k k k 是偶數時),這些元素在兩個數組中的下標范圍分別是 nums 1 \textit{nums}_1 nums1? 的下標范圍 [ index 1 , endIndex 1 ] [\textit{index}_1, \textit{endIndex}_1] [index1?,endIndex1?] nums 2 \textit{nums}_2 nums2? 的下標范圍 [ index 2 , endIndex 2 ] [\textit{index}_2, \textit{endIndex}_2] [index2?,endIndex2?],其中 endIndex 1 = index 1 + ? k ? 1 2 ? \textit{endIndex}_1 = \textit{index}_1 + \Big\lfloor \dfrac{k - 1}{2} \Big\rfloor endIndex1?=index1?+?2k?1?? endIndex 2 = index 2 + ? k ? 1 2 ? \textit{endIndex}_2 = \textit{index}_2 + \Big\lfloor \dfrac{k - 1}{2} \Big\rfloor endIndex2?=index2?+?2k?1??。考慮 nums 1 [ endIndex 1 ] \textit{nums}_1[\textit{endIndex}_1] nums1?[endIndex1?] nums 2 [ endIndex 2 ] \textit{nums}_2[\textit{endIndex}_2] nums2?[endIndex2?],其中的較大值是第 k k k 小元素(當 k k k 是奇數時)或第 k ? 1 k - 1 k?1 小元素(當 k k k 是偶數時),因此其中的較小值一定不是第 k k k 小元素。對于較小值所在的數組,可以將較小值以及較小值前面的元素全部排除。

需要注意的是, endIndex 1 \textit{endIndex}_1 endIndex1? endIndex 2 \textit{endIndex}_2 endIndex2? 不能超出數組下標范圍。如果一個數組的剩余元素個數少于 ? k 2 ? \Big\lceil \dfrac{k}{2} \Big\rceil ?2k??,則該數組中考慮的元素是該數組中的全部剩余元素。因此有 endIndex 1 = min ? ( index 1 + ? k ? 1 2 ? , m ? 1 ) \textit{endIndex}_1 = \min(\textit{index}_1 + \Big\lfloor \dfrac{k - 1}{2} \Big\rfloor, m - 1) endIndex1?=min(index1?+?2k?1??,m?1) endIndex 2 = min ? ( index 2 + ? k ? 1 2 ? , n ? 1 ) \textit{endIndex}_2 = \min(\textit{index}_2 + \Big\lfloor \dfrac{k - 1}{2} \Big\rfloor, n - 1) endIndex2?=min(index2?+?2k?1??,n?1)。

由此可以根據三種情況分別做相應的處理,縮小查找范圍。

  • 如果 nums 1 [ endIndex 1 ] < nums 2 [ endIndex 2 ] \textit{nums}_1[\textit{endIndex}_1] < \textit{nums}_2[\textit{endIndex}_2] nums1?[endIndex1?]<nums2?[endIndex2?],則將 nums 1 \textit{nums}_1 nums1? 的下標范圍 [ index 1 , endIndex 1 ] [\textit{index}_1, \textit{endIndex}_1] [index1?,endIndex1?] 中的元素全部排除,排除的元素個數是 endIndex 1 ? index 1 + 1 \textit{endIndex}_1 - \textit{index}_1 + 1 endIndex1??index1?+1。

  • 如果 nums 1 [ endIndex 1 ] > nums 2 [ endIndex 2 ] \textit{nums}_1[\textit{endIndex}_1] > \textit{nums}_2[\textit{endIndex}_2] nums1?[endIndex1?]>nums2?[endIndex2?],則將 nums 2 \textit{nums}_2 nums2? 的下標范圍 [ index 2 , endIndex 2 ] [\textit{index}_2, \textit{endIndex}_2] [index2?,endIndex2?] 中的元素全部排除,排除的元素個數是 endIndex 2 ? index 2 + 1 \textit{endIndex}_2 - \textit{index}_2 + 1 endIndex2??index2?+1。

  • 如果 nums 1 [ endIndex 1 ] = nums 2 [ endIndex 2 ] \textit{nums}_1[\textit{endIndex}_1] = \textit{nums}_2[\textit{endIndex}_2] nums1?[endIndex1?]=nums2?[endIndex2?],則處理方式和 nums 1 [ endIndex 1 ] < nums 2 [ endIndex 2 ] \textit{nums}_1[\textit{endIndex}_1] < \textit{nums}_2[\textit{endIndex}_2] nums1?[endIndex1?]<nums2?[endIndex2?] 相同。

每次查找之后,將 k k k 的值減去排除的元素個數,并將排除元素的數組的相應下標更新為該數組首個剩余元素的下標,具體做法如下:如果排除的是 nums 1 \textit{nums}_1 nums1? 中的元素,則將 index 1 \textit{index}_1 index1? 更新為 endIndex 1 + 1 \textit{endIndex}_1 + 1 endIndex1?+1;如果排除的是 nums 2 \textit{nums}_2 nums2? 中的元素,則將 index 2 \textit{index}_2 index2? 更新為 endIndex 2 + 1 \textit{endIndex}_2 + 1 endIndex2?+1。

二分查找的條件是 index 1 < m \textit{index}_1 < m index1?<m index 2 < n \textit{index}_2 < n index2?<n k > 0 k > 0 k>0。如果三個條件之一不滿足,則二分查找結束,得到目標值。

  • 如果 index 1 = m \textit{index}_1 = m index1?=m,則剩余元素都在 nums 2 \textit{nums}_2 nums2? 中,目標值是 nums 2 [ index 2 + k ] \textit{nums}_2[\textit{index}_2 + k] nums2?[index2?+k]。

  • 如果 index 2 = n \textit{index}_2 = n index2?=n,則剩余元素都在 nums 1 \textit{nums}_1 nums1? 中,目標值是 nums 1 [ index 1 + k ] \textit{nums}_1[\textit{index}_1 + k] nums1?[index1?+k]

  • 如果 k = 0 k = 0 k=0,則剩余元素中的最小元素是目標值,目標值是 min ? ( nums 1 [ index 1 ] , nums 2 [ index 2 ] ) \min(\textit{nums}_1[\textit{index}_1], \textit{nums}_2[\textit{index}_2]) min(nums1?[index1?],nums2?[index2?])。

以下用一個例子說明該解法。

兩個數組是 nums 1 = [ 1 , 2 , 3 , 4 , 5 ] \textit{nums}_1 = [1, 2, 3, 4, 5] nums1?=[1,2,3,4,5] nums 2 = [ 1 , 2 , 3 , 4 , 5 , 6 , 7 , 8 , 9 , 10 ] \textit{nums}_2 = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10] nums2?=[1,2,3,4,5,6,7,8,9,10],兩個數組的長度分別是 m = 5 m = 5 m=5 n = 10 n = 10 n=10,長度之和是 15 15 15 k = 7 k = 7 k=7。初始時, index 1 = 0 \textit{index}_1 = 0 index1?=0 index 2 = 0 \textit{index}_2 = 0 index2?=0

  1. 根據 index 1 = 0 \textit{index}_1 = 0 index1?=0 index 2 = 0 \textit{index}_2 = 0 index2?=0 k = 7 k = 7 k=7 計算得到 endIndex 1 = 3 \textit{endIndex}_1 = 3 endIndex1?=3 endIndex 2 = 3 \textit{endIndex}_2 = 3 endIndex2?=3。由于 nums 1 [ 3 ] = nums 2 [ 3 ] \textit{nums}_1[3] = \textit{nums}_2[3] nums1?[3]=nums2?[3],因此將 nums 1 \textit{nums}_1 nums1? 的下標范圍 [ 0 , 3 ] [0, 3] [0,3] 排除,排除 4 4 4 個元素,更新得到 k = 3 k = 3 k=3 index 1 = 4 \textit{index}_1 = 4 index1?=4。

  2. 根據 index 1 = 4 \textit{index}_1 = 4 index1?=4 index 2 = 0 \textit{index}_2 = 0 index2?=0 k = 3 k = 3 k=3 計算得到 endIndex 1 = 4 \textit{endIndex}_1 = 4 endIndex1?=4 endIndex 2 = 1 \textit{endIndex}_2 = 1 endIndex2?=1。由于 nums 1 [ 4 ] > nums 2 [ 1 ] \textit{nums}_1[4] > \textit{nums}_2[1] nums1?[4]>nums2?[1],因此將 nums 2 \textit{nums}_2 nums2? 的下標范圍 [ 0 , 1 ] [0, 1] [0,1] 排除,排除 2 2 2 個元素,更新得到 k = 1 k = 1 k=1 index 2 = 2 \textit{index}_2 = 2 index2?=2

  3. 根據 index 1 = 4 \textit{index}_1 = 4 index1?=4 index 2 = 2 \textit{index}_2 = 2 index2?=2 k = 1 k = 1 k=1 計算得到 endIndex 1 = 4 \textit{endIndex}_1 = 4 endIndex1?=4 endIndex 2 = 2 \textit{endIndex}_2 = 2 endIndex2?=2。由于 nums 1 [ 4 ] > nums 2 [ 2 ] \textit{nums}_1[4] > \textit{nums}_2[2] nums1?[4]>nums2?[2],因此將 nums 2 \textit{nums}_2 nums2? 的下標范圍 [ 2 , 2 ] [2, 2] [2,2] 排除,排除 1 1 1 個元素,更新得到 k = 0 k = 0 k=0 index 2 = 3 \textit{index}_2 = 3 index2?=3

  4. 此時 k = 0 k = 0 k=0,二分查找結束, nums 1 [ 4 ] \textit{nums}_1[4] nums1?[4] nums 2 [ 3 ] \textit{nums}_2[3] nums2?[3] 中的較小值 4 4 4 即為目標值。

代碼

class Solution {public double findMedianSortedArrays(int[] nums1, int[] nums2) {int m = nums1.length, n = nums2.length;int total = m + n;if (total % 2 == 1) {int medianIndex = (total - 1) / 2;return findKthSmallest(medianIndex, nums1, nums2);} else {int medianIndex1 = total / 2 - 1, medianIndex2 = total / 2;return (findKthSmallest(medianIndex1, nums1, nums2) + findKthSmallest(medianIndex2, nums1, nums2)) / 2.0;}}public int findKthSmallest(int k, int[] nums1, int[] nums2) {int m = nums1.length, n = nums2.length;int index1 = 0, index2 = 0;while (index1 < m && index2 < n && k > 0) {int endIndex1 = Math.min(index1 + (k - 1) / 2, m - 1);int endIndex2 = Math.min(index2 + (k - 1) / 2, n - 1);int num1 = nums1[endIndex1], num2 = nums2[endIndex2];if (num1 <= num2) {k -= endIndex1 - index1 + 1;index1 = endIndex1 + 1;} else {k -= endIndex2 - index2 + 1;index2 = endIndex2 + 1;}}if (index1 == m) {return nums2[index2 + k];} else if (index2 == n) {return nums1[index1 + k];} else {return Math.min(nums1[index1], nums2[index2]);}}
}

復雜度分析

  • 時間復雜度: O ( log ? ( m + n ) ) O(\log (m + n)) O(log(m+n)),其中 m m m n n n 分別是數組 nums 1 \textit{nums}_1 nums1? nums 2 \textit{nums}_2 nums2? 的長度。每次尋找第 k k k 小元素時, k k k 的初始值是 m + n m + n m+n 的一半附近的整數,每次查找將 k k k 的值減小一半,因此時間復雜度是 O ( log ? ( m + n ) ) O(\log (m + n)) O(log(m+n))

  • 空間復雜度: O ( 1 ) O(1) O(1)。

解法二

思路和算法

解法一的時間復雜度是 O ( log ? ( m + n ) ) O(\log (m + n)) O(log(m+n)),該時間復雜度已經很低,但是這道題還存在時間復雜度更低的解法。

為了找到中位數,需要在數組 nums 1 \textit{nums}_1 nums1? nums 2 \textit{nums}_2 nums2? 中分別找到分割點 cut 1 \textit{cut}_1 cut1? cut 2 \textit{cut}_2 cut2?,將每個數組分割成兩個部分。

  • 數組 nums 1 \textit{nums}_1 nums1? 被分割成下標范圍 [ 0 , cut 1 ? 1 ] [0, \textit{cut}_1 - 1] [0,cut1??1] 和下標范圍 [ cut 1 , m ? 1 ] [\textit{cut}_1, m - 1] [cut1?,m?1] 兩部分,左邊部分的長度是 cut 1 \textit{cut}_1 cut1?。

  • 數組 nums 2 \textit{nums}_2 nums2? 被分割成下標范圍 [ 0 , cut 2 ? 1 ] [0, \textit{cut}_2 - 1] [0,cut2??1] 和下標范圍 [ cut 2 , n ? 1 ] [\textit{cut}_2, n - 1] [cut2?,n?1] 兩部分,左邊部分的長度是 cut 2 \textit{cut}_2 cut2?。

其中, 0 ≤ cut 1 ≤ m 0 \le \textit{cut}_1 \le m 0cut1?m 0 ≤ cut 2 ≤ n 0 \le \textit{cut}_2 \le n 0cut2?n,即每個數組分割成的兩個部分中可以有一個部分為空。

假設 nums 1 [ ? 1 ] = nums 2 [ ? 1 ] = ? ∞ \textit{nums}_1[-1] = \textit{nums}_2[-1] = -\infty nums1?[?1]=nums2?[?1]=? nums 1 [ m ] = nums 2 [ n ] = + ∞ \textit{nums}_1[m] = \textit{nums}_2[n] = +\infty nums1?[m]=nums2?[n]=+,分割應滿足以下兩個條件。

  • 兩個數組的左邊部分的最大值小于等于兩個數組的右邊部分的最小值, max ? ( nums 1 [ cut 1 ? 1 ] , nums 2 [ cut 2 ? 1 ] ) ≤ min ? ( nums 1 [ cut 1 ] , nums 2 [ cut 2 ] ) \max(\textit{nums}_1[\textit{cut}_1 - 1], \textit{nums}_2[\textit{cut}_2 - 1]) \le \min(\textit{nums}_1[\textit{cut}_1], \textit{nums}_2[\textit{cut}_2]) max(nums1?[cut1??1],nums2?[cut2??1])min(nums1?[cut1?],nums2?[cut2?])。

  • 兩個數組的左邊部分的長度之和為兩個數組的長度之和的一半向上取整, cut 1 + cut 2 = ? m + n 2 ? \textit{cut}_1 + \textit{cut}_2 = \Big\lceil \dfrac{m + n}{2} \Big\rceil cut1?+cut2?=?2m+n??。

將兩個數組的左邊部分統稱為前半部分,將兩個數組的右邊部分統稱為后半部分,則前半部分的最大值小于等于后半部分的最小值,前半部分的元素個數為兩個數組的長度之和的一半向上取整。

total = m + n \textit{total} = m + n total=m+n 表示兩個升序數組的長度之和,用 lowerSize = ? total 2 ? \textit{lowerSize} = \Big\lceil \dfrac{\textit{total}}{2} \Big\rceil lowerSize=?2total?? 表示前半部分的元素個數。當 total \textit{total} total 是奇數時,中位數是前半部分的最大值;當 total \textit{total} total 是偶數時,中位數是前半部分的最大值與后半部分的最小值的平均數。

由于已知 cut 1 + cut 2 = lowerSize \textit{cut}_1 + \textit{cut}_2 = \textit{lowerSize} cut1?+cut2?=lowerSize,因此可以在 nums 1 \textit{nums}_1 nums1? 中尋找 cut 1 \textit{cut}_1 cut1?,當 cut 1 \textit{cut}_1 cut1? 確定之后 cut 2 \textit{cut}_2 cut2? 也可以確定。

尋找 cut 1 \textit{cut}_1 cut1? 可以使用二分查找實現。由于兩個數組都是升序數組, nums 1 [ cut 1 ? 1 ] ≤ nums 1 [ cut 1 ] \textit{nums}_1[\textit{cut}_1 - 1] \le \textit{nums}_1[\textit{cut}_1] nums1?[cut1??1]nums1?[cut1?] nums 2 [ cut 2 ? 1 ] ≤ nums 2 [ cut 2 ] \textit{nums}_2[\textit{cut}_2 - 1] \le \textit{nums}_2[\textit{cut}_2] nums2?[cut2??1]nums2?[cut2?] 都滿足,因此只需要滿足 nums 1 [ cut 1 ? 1 ] ≤ nums 2 [ cut 2 ] \textit{nums}_1[\textit{cut}_1 - 1] \le \textit{nums}_2[\textit{cut}_2] nums1?[cut1??1]nums2?[cut2?] nums 2 [ cut 2 ? 1 ] ≤ nums 1 [ cut 1 ] \textit{nums}_2[\textit{cut}_2 - 1] \le \textit{nums}_1[\textit{cut}_1] nums2?[cut2??1]nums1?[cut1?] 即可。二分查找需要查找滿足 nums 1 [ cut 1 ? 1 ] ≤ nums 2 [ cut 2 ] \textit{nums}_1[\textit{cut}_1 - 1] \le \textit{nums}_2[\textit{cut}_2] nums1?[cut1??1]nums2?[cut2?] 的最大下標 cut 1 \textit{cut}_1 cut1?。

low \textit{low} low high \textit{high} high 分別表示二分查找的下標范圍的下界和上界,初始時 low = 0 \textit{low} = 0 low=0 high = m \textit{high} = m high=m。每次查找時,取 index 1 \textit{index}_1 index1? low \textit{low} low high \textit{high} high 的平均數向上取整,并得到 index 2 = lowerSize ? index 1 \textit{index}_2 = \textit{lowerSize} - \textit{index}_1 index2?=lowerSize?index1?,比較 nums 1 [ index 1 ? 1 ] \textit{nums}_1[\textit{index}_1 - 1] nums1?[index1??1] nums 2 [ index 2 ] \textit{nums}_2[\textit{index}_2] nums2?[index2?] 的大小關系,調整查找的下標范圍。

  • 如果 nums 1 [ index 1 ? 1 ] ≤ nums 2 [ index 2 ] \textit{nums}_1[\textit{index}_1 - 1] \le \textit{nums}_2[\textit{index}_2] nums1?[index1??1]nums2?[index2?],則 cut 1 ≥ index 1 \textit{cut}_1 \ge \textit{index}_1 cut1?index1?,因此在下標范圍 [ index 1 , high ] [\textit{index}_1, \textit{high}] [index1?,high] 中繼續(xù)查找。

  • 如果 nums 1 [ index 1 ? 1 ] > nums 2 [ index 2 ] \textit{nums}_1[\textit{index}_1 - 1] > \textit{nums}_2[\textit{index}_2] nums1?[index1??1]>nums2?[index2?],則 cut 1 < index 1 \textit{cut}_1 < \textit{index}_1 cut1?<index1?,因此在下標范圍 [ low , index 1 ? 1 ] [\textit{low}, \textit{index}_1 - 1] [low,index1??1] 中繼續(xù)查找。

low = high \textit{low} = \textit{high} low=high 時,查找結束,此時 low \textit{low} low 即為 cut 1 \textit{cut}_1 cut1?。

得到 cut 1 \textit{cut}_1 cut1? 之后即可得到 cut 2 \textit{cut}_2 cut2? nums 1 [ cut 1 ? 1 ] \textit{nums}_1[\textit{cut}_1 - 1] nums1?[cut1??1] nums 2 [ cut 2 ? 1 ] \textit{nums}_2[\textit{cut}_2 - 1] nums2?[cut2??1] 中的最大值是前半部分的最大值, nums 1 [ cut 1 ] \textit{nums}_1[\textit{cut}_1] nums1?[cut1?] nums 2 [ cut 2 ] \textit{nums}_2[\textit{cut}_2] nums2?[cut2?] 中的最小值是后半部分的最小值。根據前半部分的最大值和后半部分的最小值即可計算中位數。

  • total \textit{total} total 是奇數時,中位數是前半部分的最大值。

  • total \textit{total} total 是偶數時,中位數是前半部分的最大值與后半部分的最小值的平均數。

該解法的時間復雜度是 O ( log ? m ) O(\log m) O(logm),優(yōu)于解法一的 O ( log ? ( m + n ) ) O(\log (m + n)) O(log(m+n))。

實現方面,由于只需要在一個數組中二分查找,因此可以選擇較短的數組二分查找,時間復雜度是 O ( log ? min ? ( m , n ) ) O(\log \min(m, n)) O(logmin(m,n))。

以下用一個例子說明上述過程。

兩個數組是 nums 1 = [ 1 , 2 , 3 , 4 , 5 ] \textit{nums}_1 = [1, 2, 3, 4, 5] nums1?=[1,2,3,4,5] nums 2 = [ 1 , 2 , 3 , 4 , 5 , 6 , 7 , 8 , 9 , 10 ] \textit{nums}_2 = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10] nums2?=[1,2,3,4,5,6,7,8,9,10],兩個數組的長度分別是 m = 5 m = 5 m=5 n = 10 n = 10 n=10,長度之和是 15 15 15,前半部分的元素個數是 8 8 8。初始時, low = 0 \textit{low} = 0 low=0 high = 5 \textit{high} = 5 high=5。

  1. 根據 low = 0 \textit{low} = 0 low=0 high = 5 \textit{high} = 5 high=5 計算得到 index 1 = 3 \textit{index}_1 = 3 index1?=3 index 2 = 5 \textit{index}_2 = 5 index2?=5。由于 nums 1 [ 2 ] ≤ nums 2 [ 5 ] \textit{nums}_1[2] \le \textit{nums}_2[5] nums1?[2]nums2?[5],因此將 low \textit{low} low 更新為 3 3 3。

  2. 根據 low = 3 \textit{low} = 3 low=3 high = 5 \textit{high} = 5 high=5 計算得到 index 1 = 4 \textit{index}_1 = 4 index1?=4 index 2 = 4 \textit{index}_2 = 4 index2?=4。由于 nums 1 [ 3 ] ≤ nums 2 [ 4 ] \textit{nums}_1[3] \le \textit{nums}_2[4] nums1?[3]nums2?[4],因此將 low \textit{low} low 更新為 4 4 4。

  3. 根據 low = 4 \textit{low} = 4 low=4 high = 5 \textit{high} = 5 high=5 計算得到 index 1 = 5 \textit{index}_1 = 5 index1?=5 index 2 = 3 \textit{index}_2 = 3 index2?=3。由于 nums 1 [ 4 ] > nums 2 [ 3 ] \textit{nums}_1[4] > \textit{nums}_2[3] nums1?[4]>nums2?[3],因此將 high \textit{high} high 更新為 4 4 4

  4. 此時 low = high \textit{low} = \textit{high} low=high,二分查找結束。根據 low = 4 \textit{low} = 4 low=4 計算得到 cut 1 = 4 \textit{cut}_1 = 4 cut1?=4 cut 2 = 4 \textit{cut}_2 = 4 cut2?=4,前半部分的最大值是 4 4 4,后半部分的最小值是 5 5 5。由于兩個數組的長度之和是奇數,因此中位數是前半部分的最大值,中位數是 4 4 4。

代碼

class Solution {public double findMedianSortedArrays(int[] nums1, int[] nums2) {return nums1.length <= nums2.length ? findMedian(nums1, nums2) : findMedian(nums2, nums1);}public double findMedian(int[] shorter, int[] longer) {int length1 = shorter.length, length2 = longer.length;int total = length1 + length2;int lowerSize = (total + 1) / 2;int low = 0, high = length1;while (low < high) {int index1 = low + (high - low + 1) / 2;int index2 = lowerSize - index1;int left1 = shorter[index1 - 1];int right2 = longer[index2];if (left1 <= right2) {low = index1;} else {high = index1 - 1;}}int cut1 = low, cut2 = lowerSize - low;int lower1 = cut1 == 0 ? Integer.MIN_VALUE : shorter[cut1 - 1];int lower2 = cut2 == 0 ? Integer.MIN_VALUE : longer[cut2 - 1];int higher1 = cut1 == length1 ? Integer.MAX_VALUE : shorter[cut1];int higher2 = cut2 == length2 ? Integer.MAX_VALUE : longer[cut2];int lowerMax = Math.max(lower1, lower2), higherMin = Math.min(higher1, higher2);if (total % 2 == 1) {return lowerMax;} else {return (lowerMax + higherMin) / 2.0;}}
}

復雜度分析

  • 時間復雜度: O ( log ? min ? ( m , n ) ) O(\log \min(m, n)) O(logmin(m,n)),其中 m m m n n n 分別是數組 nums 1 \textit{nums}_1 nums1? nums 2 \textit{nums}_2 nums2? 的長度。在較短的數組中二分查找,范圍是 [ 0 , min ? ( m , n ) ] [0, \min(m, n)] [0,min(m,n)],二分查找的次數是 O ( log ? min ? ( m , n ) ) O(\log \min(m, n)) O(logmin(m,n)),每次查找的時間是 O ( 1 ) O(1) O(1),因此時間復雜度是 O ( log ? min ? ( m , n ) ) O(\log \min(m, n)) O(logmin(m,n))。

  • 空間復雜度: O ( 1 ) O(1) O(1)。

http://m.risenshineclean.com/news/63960.html

相關文章:

  • 蘇州網站建設推廣服務百度電話怎么轉人工客服
  • 怎么做網站免費的刷贊百度seo正規(guī)優(yōu)化
  • 廣州網站外貿推廣seo有哪些網站
  • 哪家手表網站鞏義網絡推廣
  • 大型網站開發(fā) 框架網絡搜索關鍵詞排名
  • 凡科做的網站為什么打不開十大跨界營銷案例
  • 做網站需要哪些素材網站優(yōu)化排名軟件
  • wordpress javascript廣告插件seo排名推廣
  • 網站做優(yōu)化多少錢牛推網
  • 汶上云速網站建設如何找做網站的公司
  • 北京微信網站建設費用北京seo優(yōu)化公司
  • 網站建設有什么方法連接數據庫網絡營銷師證
  • 政府網站建設新模式網站排名優(yōu)化軟件聯系方式
  • 開鎖都在什么網站做最有效的推廣學校的方式
  • 諸城做網站找個人種子搜索神器 bt 下載
  • 網站建設 價格新聞軟文自助發(fā)布平臺
  • 大連app制作seo外包優(yōu)化網站
  • jsp做網站能實現什么功能百度網盤搜索引擎
  • .網站開發(fā)工具dw搜索引擎付費推廣
  • .net 創(chuàng)建網站項目網絡營銷的主要特點有哪些
  • 關于網站建設相關文章武漢 網絡 推廣
  • 南京網站流量優(yōu)化輕松seo優(yōu)化排名 快排
  • 建設公司網站要注意哪些杭州網站排名提升
  • 化妝品網站建設項目計劃書今日新聞頭條
  • wordpress建站速度提升免費推廣途徑與原因
  • 深圳網站設計價格表優(yōu)化大師下載舊版本安裝
  • 山東德州如何網站建設教程qq群排名優(yōu)化
  • 廣州做和改版網站的公司網上賣貨的平臺有哪些
  • 好用的wordpress代碼編輯器河南seo外包
  • phpcms 做購物網站谷歌seo優(yōu)化公司