题目描述:
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)).
题目大意:
已排序数组nums1和nums2长度分别为m和n
找出这两个已排序数组的中位数,时间复杂度控制在O(log (m+n))
Example 1:
nums1 = [1, 3] nums2 = [2] The median is 2.0
Example 2:
nums1 = [1, 2] nums2 = [3, 4] The median is (2 + 3)/2 = 2.5
Subscribe to see which companies asked this question.
题解:
如果没有时间复杂度要求,按照归并排序中合并的思想,可以在线性时间内得到解。
如果有这一log时间复杂度的要求,那么答案基本只有二分了。
考虑取nums1和nums2的中位数a和b,
如果a < b,那么两个数组的中位数肯定不在小于a的区域,即nums1的左侧;
如果b < a,那么两个数组的中位数肯定不在小于b的区域,即nums2的左侧;
根据上述思想,每次能够扔掉数组一半的值,达到高效查找目的;
Code【Java】
public class Solution {
private int getKthNum(int[] numsA, int startA, int[] numsB, int startB, int k) {
// 处理特殊情况
if (numsA.length < startA + 1) return numsB[startB + k - 1];
if (numsB.length < startB + 1) return numsA[startA + k - 1];
if (k == 1) return Math.min(numsA[startA], numsB[startB]);
// 比较中间值
int midA = (startA + k / 2 - 1 < numsA.length) ? numsA[startA + k / 2 - 1] : Integer.MAX_VALUE;
int midB = (startB + k / 2 - 1 < numsB.length) ? numsB[startB + k / 2 - 1] : Integer.MAX_VALUE;
if (midA < midB) {
return getKthNum(numsA, startA + k / 2, numsB, startB, k - k / 2);
}
else {
return getKthNum(numsA, startA, numsB, startB + k / 2, k - k / 2);
}
}
public double findMedianSortedArrays(int[] nums1, int[] nums2) {
int len = nums1.length + nums2.length;
return (getKthNum(nums1, 0, nums2, 0, (len + 1) / 2) +
getKthNum(nums1, 0, nums2, 0, (len + 2) / 2)) / 2.0;
}
}
Code 【C++】
class Solution {
private:
const int MAX = 0x7fffffff;
int findKthNum(vector<int>& numsA, int startA, vector<int>& numsB, int startB, int k) {
// 处理特殊情况
if (numsA.size() < startA + 1) return numsB[startB + k - 1];
if (numsB.size() < startB + 1) return numsA[startA + k - 1];
if (k == 1) return min(numsA[startA], numsB[startB]);
// 比较中点 舍去部分无意义的值
int midA = (startA + k/2 - 1 < numsA.size()) ? numsA[startA + k/2 - 1] : MAX;
int midB = (startB + k/2 - 1 < numsB.size()) ? numsB[startB + k/2 - 1] : MAX;
if (midA < midB) {
return findKthNum(numsA, startA + k/2, numsB, startB, k - k/2);
}
else {
return findKthNum(numsA, startA, numsB, startB + k/2, k - k/2);
}
}
public:
double findMedianSortedArrays(vector<int>& nums1, vector<int>& nums2) {
int len = nums1.size() + nums2.size();
return (findKthNum(nums1, 0, nums2, 0, (len + 1) / 2) +
findKthNum(nums1, 0, nums2, 0, (len + 2) / 2)) / 2.0;
}
};