Median of Two Sorted Arrays

LeetCode OJ 4:There are two sorted arrays nums1 and nums2 of size m and n respectively. Find the median of the two sorted arrays. The overall run time complexity should be O(log (m+n)).

思路1:我的做法是依次比较数组A和数组B的最小元素大小,较小者的数组指针右移,直至找到两个数组的中位数。如果m+n为奇数,则中位数为第(m+n)/2+1个元素,否则中位数为第(m+n)/2和第(m+n)/2+1个元素的平均数。在这个过程中,要时刻注意数组长度的问题。

double findMedianSortedArrays(vector<int>& nums1, vector<int>& nums2) {
  int i, j, k, m, n, limit;
  double median, median1, median2;
  i = j = k = 0;
  m = nums1.size();
  n = nums2.size();

  if((m + n) % 2 == 0)
    limit = (m + n) / 2 - 1 > 0 ? (m + n) / 2 - 1 : 0;
  else
    limit = (m + n) / 2;

  while(k < limit)
  {
    if(i == m) j++;
    else if (j == n) i++; 
    else if(nums1.at(i) < nums2.at(j)) i++;
    else j++;
    k++;
  }

  if(i == m)
    median1 = nums2.at(j++);
  else if(j == n)
    median1 = nums1.at(i++);
  else
    median1 = nums1.at(i) < nums2.at(j) ? nums1.at(i++) : nums2.at(j++);

  if((m + n) % 2 == 0)
  {
    if(i == m)
      median2 = nums2.at(j++);
    else if(j == n)
      median2 = nums1.at(i++);
    else
      median2 = nums1.at(i) < nums2.at(j) ? nums1.at(i) : nums2.at(j);
    median = (median1 + median2) / 2.0;
  }
  else
    median = median1;

  return median;
}

思路2:该方法的核心是将原问题转变成一个寻找第k小数的问题(假设两个原序列升序排列),这样中位数实际上是第(m+n)/2小的数。所以只要解决了第k小数的问题,原问题也得以解决。首先假设数组A和B的元素个数都大于k/2,我们比较A[k/2-1]和B[k/2-1]两个元素,这两个元素分别表示A的第k/2小的元素和B的第k/2小的元素。这两个元素比较共有三种情况:>、<和=。如果A[k/2-1]<B[k/2-1],这表示A[0]到A[k/2-1]的元素都在A和B合并之后的前k小的元素中。换句话说,A[k/2-1]不可能大于两数组合并之后的第k小值,所以我们可以将其抛弃。

此外我们还需要考虑几个边界条件:

  • 如果A或者B为空,则直接返回B[k-1]或者A[k-1];
  • 如果k为1,我们只需要返回A[0]和B[0]中的较小值;
  • 如果A[k/2-1]=B[k/2-1],返回其中一个;
class Solution 
{ 
public:

  double findKth(int a[], int m, int b[], int n, int k) 
  { 
    if (m > n) 
      return findKth(b, n, a, m, k); 
    if (m == 0) 
      return b[k - 1]; 
    if (k == 1) 
      return min(a[0], b[0]); 
    int pa = min(k / 2, m), pb = k - pa; 
    if (a[pa - 1] < b[pb - 1]) 
      return findKth(a + pa, m - pa, b, n, k - pa); 
    else if (a[pa - 1] > b[pb - 1]) 
      return findKth(a, m, b + pb, n - pb, k - pb); 
    else 
      return a[pa - 1]; 
  }  
  double findMedianSortedArrays(int A[], int m, int B[], int n) 
  { 
    int total = m + n; 
    if (total & 0x1) 
      return findKth(A, m, B, n, total / 2 + 1); 
    else 
      return (findKth(A, m, B, n, total / 2) + findKth(A, m, B, n, total / 2 + 1)) / 2; 
  }

};

 

posted @ 2016-07-13 20:29  信步闲庭、、  阅读(164)  评论(0编辑  收藏  举报