Leetcode4(寻找两个正序数组的中位数)

题目描述

给定两个大小分别为 m 和 n 的正序(从小到大)数组 nums1 和 nums2。请你找出并返回这两个正序数组的 中位数 。

示例 1:

输入:nums1 = [1,3], nums2 = [2]
输出:2.00000
解释:合并数组 = [1,2,3] ,中位数 2
示例 2:

输入:nums1 = [1,2], nums2 = [3,4]
输出:2.50000
解释:合并数组 = [1,2,3,4] ,中位数 (2 + 3) / 2 = 2.5

提示:

nums1.length == m
nums2.length == n
0 <= m <= 1000
0 <= n <= 1000
1 <= m + n <= 2000
-106 <= nums1[i], nums2[i] <= 106

题解

如果对时间复杂度的要求有 log,通常都需要用到二分查找,这道题也可以通过二分查找实现。

debug半天写边界,还可以优化
明天优化一下,然后实现一下方法二

package com.example;

class Solution {
    public int[] nums1,nums2;
    public double findMedianSortedArrays(int[] nums1, int[] nums2) {
        this.nums1=nums1;
        this.nums2=nums2;
        int n1=nums1.length,n2=nums2.length;
        if((n1+n2)%2==1){
            return find((n1+n2)/2+1);
        }
        return (find((n1+n2)/2+1)+find((n1+n2)/2))*1.0/2;
    }
    public int find(int k){
        int l1=0,l2=0;
        int n1=nums1.length,n2=nums2.length;
        while(true){
            if(l1==n1) return nums2[l2+k-1];
            if(l2==n2) return nums1[l1+k-1];
            if(k==1){
                return nums1[l1]>nums2[l2]?nums2[l2]:nums1[l1];
            }
            int mid=(k/2)-1;
            if(l1+mid>=n1&&n1<=n2){
                mid=n1-l1-1;
            }
            if(l2+mid>=n2&&n1>=n2){
                mid=n2-l2-1;
            }
            if(nums1[l1+mid]>=nums2[l2+mid]){
                l2+=mid+1;
                k-=mid+1;
            }
            else{
                l1+=mid+1;
                k-=mid+1;
            }
        }
    }
}

先放这里、边界还是没那么清楚

class Solution {
    public double findMedianSortedArrays(int[] nums1, int[] nums2) {
        int n1=nums1.length,n2=nums2.length;
        if(n1<=n2) return find(nums1,nums2);
        else return find(nums2,nums1);
    }
    public double find(int[] nums1,int[] nums2){
        int l=-1,r=nums1.length+1;
        while(l+1!=r){
            int mid=l+(r-l)/2;
            if(check(nums1,nums2,mid)){
                l=mid;
            }
            else r=mid;
        }
        int nums1l=l==0?Integer.MIN_VALUE:nums1[l-1];
        int nums1r=l==nums1.length?Integer.MAX_VALUE:nums1[l];
        int j=(nums1.length+nums2.length+1)/2-l;
        int nums2l=j==0?Integer.MIN_VALUE:nums2[j-1];
        int nums2r=j==nums2.length?Integer.MAX_VALUE:nums2[j];
        if((nums1.length+nums2.length)%2==0){
            return (Math.max(nums1l,nums2l)+Math.min(nums1r,nums2r))/2.0;
        }
        else return Math.max(nums1l,nums2l);
    }
    public boolean check(int[] nums1,int[] nums2,int mid){
        int i=mid,j=(nums1.length+nums2.length+1)/2-mid;
        int nums1l=i==0?Integer.MIN_VALUE:nums1[i-1];
        int nums2r=j==nums2.length?Integer.MAX_VALUE:nums2[j];
        if(nums1l<=nums2r) return true;
        else return false;
    }
}

你可能感兴趣的:(算法)