问题
给定两个大小为 m 和 n 的有序数组 nums1 和 nums2。
请你找出这两个有序数组的中位数,并且要求算法的时间复杂度为 O(log(m + n))。
你可以假设 nums1 和 nums2 不会同时为空
例子
思路
- 方法1 O(m+n) O(m+n)
构造一个数组nums,长度为nums1.length+nums2.length+2,将nums1和nums2中的数按序填入nums,最后得出结果
- 方法2 O(m+n) O(1)
无需构造数组,只需要知道中位数的两个数即可
L_index = (len-1)/2
R_index=len/2
- 方法3 O(log(m+n)) O(1)
代码
//方法1
//方法2
class Solution {
public double findMedianSortedArrays(int[] nums1, int[] nums2) {
int len1 = nums1.length, len2=nums2.length;
int len=len1+len2;
int i=0, j=0,m=0,L=0,R=0,num=0;
while (i<len1 || j<len2) {
int num1 = i==len1? (1<<31)-1:nums1[i];
int num2 = j==len2? (1<<31)-1:nums2[j];
if (num1<num2) {
num=num1;
i++;
} else {
num=num2;
j++;
}
if ((len-1)/2==m) L=num;
if ((len/2)==m) {
R=num;
break;
}
m++;
}
return (L+R)/2.0;
}
}
//方法3 O(log(m+n))
class Solution {
public double findMedianSortedArrays(int[] nums1, int[] nums2) {
int m=nums1.length,n=nums2.length;
//left,right是第几个,
int left = (m+n+1)/2;
int right = (m+n+2)/2;
return (get(nums1,0,nums2,0,left)+get(nums1,0,nums2,0,right))/2.0;
}
public int get(int[] nums1, int i1, int[] nums2, int i2, int k){
//有数组已经走到空了
if(i1>=nums1.length) return nums2[i2+k-1];
if(i2>=nums2.length) return nums1[i1+k-1];
//两个数组都没走到空
//找最小的
if(k==1) return Math.min(nums1[i1], nums2[i2]);
//从k中去掉k/2个
//分别找第k/2个,如果不存在,赋值MAX
int a = i1+k/2-1<nums1.length?nums1[i1+k/2-1]:Integer.MAX_VALUE;
int b = i2+k/2-1<nums2.length?nums2[i2+k/2-1]:Integer.MAX_VALUE;
if(a<b)
return get(nums1,i1+k/2,nums2,i2,k-k/2);
else
return get(nums1,i1,nums2,i2+k/2,k-k/2);
}
}