zoukankan      html  css  js  c++  java
  • LeetCode——寻找两个正序数组的中位数

    题目地址:https://leetcode-cn.com/problems/median-of-two-sorted-arrays/

    解题思路:方法一:判断中位数位置,同时从两个数组中筛选。(时间复杂度O(m+n))

         方法二:二分查找(时间复杂度O(log(m+n)))

    方法一

    double findMedianSortedArrays(int* nums1, int nums1Size, int* nums2, int nums2Size) {
        int i, j;
        //判断总数奇偶
        bool check = (nums1Size + nums2Size) & 1;
        //判断中心位置
        int midIndex = check ? (nums1Size + nums2Size) / 2 + 1 : (nums1Size + nums2Size) / 2;
        double median = 0.0;
        int index;//当前位置(基于整体)
        i = j = 0;
        index = 0;
        //判断空数组的情况
        if (check) {
            if (!nums1Size)
                return nums2[midIndex-1];
            else if (!nums2Size)
                return nums1[midIndex-1];
        }
        else {
            if (!nums1Size)
                return (nums2[midIndex] + nums2[midIndex - 1]) / 2.0;
            else if (!nums2Size)
                return (nums1[midIndex] + nums1[midIndex - 1]) / 2.0;
        }
    
        while (i < nums1Size && j < nums2Size && index < midIndex) {
            if (nums1[i] < nums2[j])
                median = nums1[i++];
            else
                median = nums2[j++];
            index++;
        }
        while (i < nums1Size && index < midIndex) {
            median = nums1[i++];
            index++;
        }
        while (j < nums2Size && index < midIndex) {
            median = nums2[j++];
            index++;
        }
        //奇数
        if (check)
            return median * 1.0;
        else {
            if (i == nums1Size)
                return (median + nums2[j]) / 2.0;
            else if (j == nums2Size)
                return (median + nums1[i]) / 2.0;
            else
                return nums1[i] > nums2[j] ? (median + nums2[j]) / 2.0 : (median + nums1[i]) / 2.0;
        }
    }

    方法二:因为是两个有序数组,所以求中位数可以转化成寻找两个有序数组中的第k小的数。(题目要求的时间复杂度,具体理解:https://leetcode-cn.com/problems/median-of-two-sorted-arrays/solution/xun-zhao-liang-ge-you-xu-shu-zu-de-zhong-wei-s-114/

    int getKNum(int* nums1, int nums1Size, int* nums2, int nums2Size, int k)
    {
        int i, j, ii, jj;//i,j表示变化前的下标;ii,jj是变化后的下标(经过剔除操作后)
        i = j = 0;
        while (true) {
            if (i == nums1Size)//第一组数组都被剔除
                return nums2[j + k - 1];//在进行一轮剔除操作后,由于第一组数组全部被剔除,所以需要在第二组剔除剩余k-1个数
            if (j == nums2Size)//第二组数组都被剔除
                return nums1[i + k - 1];
            if (k == 1)//说明只剩下一个,判断大小即可,小的那个就是整个数组第k小的数
                return nums1[i] < nums2[j] ? nums1[i] : nums2[j];
            
            //可能数组不够k/2-1个数,所以需要判断与数组长度的关系
             ii = (i + k / 2 - 1) < (nums1Size - 1) ? (i + k / 2 - 1) : (nums1Size - 1);
             jj = (j + k / 2 - 1) < (nums2Size - 1) ? (j + k / 2 - 1) : (nums2Size - 1);
            if (nums1[ii] < nums2[jj]) {
                k -= ii - i + 1;//第一组数组剔除的个数
                i =ii+1;
            }
            else {
                k -= jj - j + 1;//第二组数组剔除的个数
                j = jj + 1;
            }
        }
    }
    double findMedianSortedArrays(int* nums1, int nums1Size, int* nums2, int nums2Size) {
        bool check = (nums1Size + nums2Size) & 1;
        if (check)
            return getKNum(nums1, nums1Size, nums2, nums2Size, (nums1Size + nums2Size) / 2 + 1) / 1.0;
        else
            return (getKNum(nums1, nums1Size, nums2, nums2Size, (nums1Size + nums2Size) / 2 + 1) + getKNum(nums1, nums1Size, nums2, nums2Size, (nums1Size + nums2Size) / 2)) / 2.0;
    }
  • 相关阅读:
    GNU安装
    camera链接
    右键terminal
    Angular cli 常见问题
    Angular路由复用策略RouteReuseStrategy
    angular5 websocket 服务
    promise 极简版封装
    js a 标签 通过download 实现下载功能
    angular6 升级到 angular7+ 最新Ng-zorro
    最新IDEA永久激活
  • 原文地址:https://www.cnblogs.com/cc-xiao5/p/13255997.html
Copyright © 2011-2022 走看看