LeetCode.4寻找两个正序数组的中位数

问题描述

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

算法的时间复杂度应该为 O(log (m+n)) 。

解题思路1

理解问题的关键是要意识到,对于一个已排序的数组或两个数组的合并体,中位数将数组分为左右两部分,其中左部分的元素数量等于右部分或多一个。

使用二分查找

为了实现 O(log (m+n)) 的时间复杂度,我们需要使用二分查找来逻辑上定位两个数组的中位数,而不是实际合并两个数组。我们的目标是通过逻辑上分割这两个数组,找到一个点,使得左边的所有元素都小于右边的元素。

二分查找的切入点
  • 对较小的数组进行二分查找(为了降低复杂度),这通常是 nums1(如果 nums1 长度大于 nums2,则交换它们)。
  • 我们定义两个指针 ij 分别在 nums1nums2 中进行移动。这两个指针的位置将数组分为左右两部分。
  • 设定两个数组中的左右分割线,nums1[i-1]nums1[i]nums2[j-1]nums2[j]
条件检查
  1. 确保 nums1[i-1] <= nums2[j]nums2[j-1] <= nums1[i]
  2. 如果以上条件不满足,根据情况调整 ij 的值。
计算中位数
  • 如果 m+n 是奇数,中位数是左边最大的数。
  • 如果是偶数,中位数是左边最大数和右边最小数的平均值。

算法步骤

  1. 确定总长度的一半 halfLen = (m + n + 1) / 2
  2. nums1 上使用二分查找:
    • 计算 ilowhigh 的中点。
    • 根据 i 计算 j = halfLen - i
    • 检查分割是否正确,如果不正确调整 lowhigh
  3. 根据上述分割计算中位数。

代码实现:

class Solution {
public:double findMedianSortedArrays(vector<int>& nums1, vector<int>& nums2) {if (nums1.size() > nums2.size()) {return findMedianSortedArrays(nums2, nums1);}int m = nums1.size();int n = nums2.size();int low = 0, high = m, halfLen = (m + n + 1) / 2;while (low <= high) {int i = (low + high) / 2;int j = halfLen - i;if (i < high && nums2[j - 1] > nums1[i]) {low = i + 1;} else if (i > low && nums1[i - 1] > nums2[j]) {high = i - 1;} else {int maxLeft = 0;if (i == 0) {maxLeft = nums2[j - 1];} else if (j == 0) {maxLeft = nums1[i - 1];} else {maxLeft = std::max(nums1[i - 1], nums2[j - 1]);}if ((m + n) % 2 == 1) {return maxLeft;}int minRight = 0;if (i == m) {minRight = nums2[j];} else if (j == n) {minRight = nums1[i];} else {minRight = std::min(nums1[i], nums2[j]);}return (maxLeft + minRight) / 2.0;}}return 0.0;}
};

优化改进

我们的目标是在不实际合并两个数组的情况下找到中位数。使用二分查找在一个较短的数组上寻找正确的分割线,然后验证这个分割线在第二个数组中是否有效。这里的关键是通过适当的分割,使得合并后数组的左半部和右半部元素数量相等或左半部多一个元素。

改进点

  1. 精简边界条件检查:避免重复或不必要的条件判断。
  2. 优化循环条件:确保二分查找的边界调整是最精确的。

代码实现:

class Solution {
public:double findMedianSortedArrays(vector<int>& nums1, vector<int>& nums2) {if (nums1.size() > nums2.size()) {return findMedianSortedArrays(nums2, nums1);}int m = nums1.size();int n = nums2.size();int low = 0, high = m;while (low <= high) {int i = (low + high) / 2;int j = (m + n + 1) / 2 - i;int maxLeftX = (i == 0) ? INT_MIN : nums1[i - 1];int minRightX = (i == m) ? INT_MAX : nums1[i];int maxLeftY = (j == 0) ? INT_MIN : nums2[j - 1];int minRightY = (j == n) ? INT_MAX : nums2[j];if (maxLeftX <= minRightY && maxLeftY <= minRightX) {if ((m + n) % 2 == 0) {return (std::max(maxLeftX, maxLeftY) +std::min(minRightX, minRightY)) /2.0;} else {return std::max(maxLeftX, maxLeftY);}} else if (maxLeftX > minRightY) {high = i - 1;} else {low = i + 1;}}return -1;}
};

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/bicheng/36943.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

hbase 优化节点进程停止方式

一、命令 /usr/local/fqlhadoop/hbase/bin/graceful_stop.sh 4.hadoop3.com日志&#xff1a; [biadmin4 ~]$ /usr/local/fqlhadoop/hbase/bin/graceful_stop.sh 4.hadoop3.com 2024-06-24T09:42:27 Disabling load balancer log4j:WARN No such property [maxBackupIndex] in…

spring boot 3.0.1多模块项目使用nacos动态配置

根pom文件增加&#xff0c;spring-cloud-alibaba包管理&#xff0c;注意版本spring-boot 3.0.3&#xff0c;spring-cloud-alibaba 2022.0.0.0-RC1 <?xml version"1.0" encoding"UTF-8"?> <project xmlns"http://maven.apache.org/POM/4.0…

学习笔记——交通安全分析10

目录 前言 当天学习笔记整理 4信控交叉口交通安全分析 结束语 前言 #随着上一轮SPSS学习完成之后&#xff0c;本人又开始了新教材《交通安全分析》的学习 #整理过程不易&#xff0c;喜欢UP就点个免费的关注趴 #本期内容接上一期09笔记 当天学习笔记整理 4信控交叉口交…

我的创作纪念日学期总结

&#x1f525;个人主页&#xff1a; Forcible Bug Maker &#x1f525;专栏&#xff1a; 关于博主 目录 &#x1f308;前言&#x1f525;我的期末考试&#x1f525;我的学期总结&#x1f525;对未来的展望&#x1f308;结语 &#x1f308;前言 本篇博客主要内容&#xff1a;博…

归并排序和计数排序

目录 1.归并排序1.1递归1.1基本思想1.2算法描述1.3画图解释1.4代码实现 1.2非递归 2.计数排序2.1基本思想2.2算法描述3.画图解释 1.归并排序 1.1递归 1.1基本思想 归并排序是建立在归并操作上的一种有效的排序算法。该算法是采用分治法&#xff08;Divide and Conquer&#xf…

【C++】动态内存管理new和delete

文章目录 一、C的内存管理方式二、new和delete的用法1.操作内置类型2.操作自定义内置类型 三、new和delete的底层实现1.operator new和operator delete函数2.new和delete的实现原理 四、定位new表达式五、malloc/free和new/delete的区别 一、C的内存管理方式 之前在C语言的动态…

kafka(四)消息类型

一、同步消息 1、生产者 同步发送的意思就是&#xff0c;一条消息发送之后&#xff0c;会阻塞当前线程&#xff0c;直至返回 ack。 由于 send 方法返回的是一个 Future 对象&#xff0c;根据 Futrue 对象的特点&#xff0c;我们也可以实现同 步发送的效果&#xff0c;只需在调…

【数据结构】计数排序等排序

&#x1f4e2;博客主页&#xff1a;https://blog.csdn.net/2301_779549673 &#x1f4e2;欢迎点赞 &#x1f44d; 收藏 ⭐留言 &#x1f4dd; 如有错误敬请指正&#xff01; &#x1f4e2;本文由 JohnKi 原创&#xff0c;首发于 CSDN&#x1f649; &#x1f4e2;未来很长&#…

C 语言实例 - 查找数组中最大的元素值

查找数组中最大的元素值。 实例 1 #include <stdio.h>int main() {int array[10] {1, 2, 3, 4, 5, 6, 7, 8, 9, 0};int loop, largest;largest array[0];for(loop 1; loop < 10; loop) {if( largest < array[loop] ) largest array[loop];}printf("最大…

Ubuntu系统中创建桌面快捷方式和添加Favorites

一. Ubuntu系统中创建软件的桌面快捷方式 Ubuntu桌面创建某个软件的桌面快捷方式&#xff0c;一个直观的方法。 方法1. 在图像界面下&#xff0c;一层一层地打开文件目录软件快捷方式/usr/share/applications/ 方法2. 或者在终端运行$ nautilus /usr/share/applications/ …

Django靓号管理系统:实现注销功能和重构视图

1. 重构项目结构 首先,我们需要重构项目结构,以更好地组织代码: 在​​web​​目录下创建一个新的​​views​​目录。在​​views​​目录中创建一个新文件​​account.py​​。删除原来的​​views.py​​文件。这样的结构更有利于代码的模块化和维护。 2. 更新 ​​url…

springcloud-config git配置源加载(部署公钥问题)

使用gitUrl作为配置源 gitee 或者github 中有类似于发布密钥的功能&#xff0c;允许通过私钥只读访问指定的仓库&#xff0c;文档中说的是 限制了git的操作为pull 和 clone。生成私钥的方式文档连接在此 https://gitee.com/help/articles/4181#article-header0 spring config只…

简过网:不懂就要问,什么叫考事业单位编制?

不懂就要问&#xff0c;什么叫考事业单位编制&#xff1f;考事业编就是纳入编制的事业单位招聘考试&#xff0c;本质上是还是一种招聘考试&#xff0c;由于是“铁饭碗”&#xff0c;福利好&#xff0c;待遇高&#xff0c;所以对于事业单位的考试一直受人关注。 ​ 一、什么是事…

深度分析 Apache Hudi:大数据实时处理的利器

什么是 Apache Hudi&#xff1f; Apache Hudi&#xff08;Hadoop Upsert Delete and Incremental&#xff09;是一个开源的数据湖存储框架&#xff0c;旨在在大规模数据集上提供高效的增量数据处理和实时数据更新能力。Hudi 由 Uber 开发&#xff0c;并于 2019 年捐赠给 Apach…

精准校准:深入解析scikit-learn中的StandardScaler

精准校准&#xff1a;深入解析scikit-learn中的StandardScaler 在机器学习中&#xff0c;特征缩放是一个至关重要的预处理步骤&#xff0c;它能够显著影响模型的性能。scikit-learn提供了一个强大的工具——StandardScaler&#xff0c;用于将数据标准化到单位方差和零均值。本…

MQ - RabbitMQ、SpringAMQP --学习笔记

什么是MQ&#xff1f; MQ 是消息队列&#xff08;Message Queue&#xff09;的缩写&#xff0c;它是一种应用程序间异步通信的技术。消息队列允许应用程序或服务间通过发送消息来交换数据&#xff0c;而不是直接调用对方&#xff0c;从而实现解耦、异步处理和负载均衡等目的。…

零成本打造精品宣传册

​随着互联网的发展&#xff0c;企业和个人对宣传册的需求日益增长&#xff0c;然而&#xff0c;高质量的宣传册制作往往需要不菲的成本。那么&#xff0c;如何零成本打造精品宣传册呢&#xff1f; 一、明确定位和目标群体 在制作宣传册之前&#xff0c;首先要明确其定位和目标…

qt pro文件常用配置

概述 记录一下常用的项目pro文件的一些常用配置 常用配置 QT core gui concurrent#添加concurrent并行处理模块 CONFIG windeployqt#打包部署&#xff0c;项目->构建步骤->Make参数 添加windeployqt&#xff0c;编译自动打包greaterThan(QT_MAJOR_VERSION, 4):…

Kafka入门到精通(三)-Kafka

Kafka简介 Kafka是由Apache软件基金会开发的一个开源流处理平台&#xff0c;由Scala和Java编写。Kafka是一种高吞吐量的分布式发布订阅消息系统&#xff0c;它可以处理消费者在网站中的所有动作流数据。 这种动作&#xff08;网页浏览&#xff0c;搜索和其他用户的行动&#xf…

强化学习-3深度学习基础

文章目录 1 强化学习与深度学习的关系2 线性回归3 梯度下降4 逻辑回归5 全连接网络6 更高级的神经网络6.1 卷积神经网络6.2 循环神经网络6.3 transformer 将深度学习和强化学习结合起来&#xff0c;利用深度学习网络强大的拟合能力通过将状态、动作等作为输入&#xff0c;来估计…