您的位置:首页 > 其它

两个有序数组的中位数

2017-06-10 18:30 337 查看
/*
* 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)).

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
* */
public class Solution {

public static void main(String[] args) {
// TODO 自动生成的方法存根
int[] nums1 = { 1,2 };
int[] nums2 = {3,4};
System.out.println(Solution.findMedianSortedArrays(nums1, nums2));
System.out.println(Solution.findMedianSortedArrays2(nums1, nums2));
}

/*
* 归并排序,但是只要排序到一半时就可以终止,得到此时i,j分别指向两个有序数组的的位置 第二步,如果两个数组的总个数为奇数,则返回i 和 j
* 所指向的元素的更大者即可;
*
* 若为偶数,需要利用i 和 j 所指向的元素大小进行讨论。
*
* 若i 所指向的元素更大,则循环中最后的遍历落在了 nums1 中,那么,如果 i−1>=0 (即i
* 前存在前一个元素)且nums1[i−1]>=nums2[j] , 则中位数为 (nums1[i−1]+nums1[i])/2.0; 如果
* i−1<0 或者 nums1[i−1]<nums2[j],则中位数为 (nums1[i]+nums2[j])/2.0 ;若落在了 nums2
* 中,则对称地进行讨论。
*/

// 这种方法空间复杂度为1,
public static double findMedianSortedArrays(int[] nums1, int[] nums2) {
int i = 0, j = 0;// 分别指向两个有序数组的位置
int len1 = nums1.length, len2 = nums2.length;
int sumpointer = 0;// 中间位置个数
for (i = 0, j = 0; (i < len1 || j < len2) && sumpointer <= (len1 + len2) >> 1; ++sumpointer) {
if (i >= len1)// len2 > len1
++j;
else if (j >= len2)// len1 > len2
++i;
else if (nums1[i] >= nums2[j])
++j;
else
++i;
}

boolean isEven = (len1 + len2) % 2 == 0;
--i;
--j;// 在上面的for循环中,对i,j对进行了一次+操作
// 判断nums1,nums2是否有空数组,也来处理边界情况,如len1 = 1,len2 = 0;
if (i < 0)
return isEven ? (nums2[j - 1] + nums2[j]) / 2.0 : nums2[j];
if (j < 0)
return isEven ? (nums1[i - 1] + nums1[i]) / 2.0 : nums1[i];

// 当总个数为奇数的时候
if (!isEven)
return Math.max(nums1[i], nums2[j]);

// 当总个数为偶数的时候
if (nums1[i] < nums2[j]) {
if (j - 1 >= 0 && nums1[i] < nums2[j - 1])
return (nums2[j] + nums2[j - 1]) / 2.0;
return (nums2[j] + nums1[i]) / 2.0;
} else {
if (i - 1 >= 0 && nums2[j] < nums1[i - 1])
return (nums1[i] + nums1[i - 1]) / 2.0;
return (nums2[j] + nums1[i]) / 2.0;
}
}

// 若新建一个数组,则为n+m,而且time长
public static double findMedianSortedArrays2(int[] nums1, int[] nums2) {
int len1 = nums1.length, len2 = nums2.length;
int[] arrNew = new int[len1 + len2];
int s1 = 0;// nums1的位置
int s2 = 0;// nums2的位置
int len = arrNew.length;
for (int i = 0; i < len; ++i) {
if ((s2 >= len2) || (s1 < len1 && nums1[s1] < nums2[s2])) {
arrNew[i] = nums1[s1];
++s1;
} else {
arrNew[i] = nums2[s2];
++s2;
}
}
// 偶数个
if (len % 2 == 0)
return (arrNew[len / 2 - 1] + arrNew[len / 2]) / 2.0;
else
return arrNew[len / 2];
}

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: