news 2026/4/18 3:37:57

面试必看:优势洗牌

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
面试必看:优势洗牌

贪心+双指针求解优势洗牌问题(C++ 实现)

题目描述

给定两个长度相等的数组nums1nums2,定义nums1相对于nums2的优势为满足nums1[i] > nums2[i]的索引i的数量。要求返回nums1的任意一个排列,使得该排列相对于nums2的优势最大化。

问题分析

结合题目要求和数据特征,我们可以先梳理核心约束与解题思路:

  1. 两个数组长度相同,排列后元素需按索引一一对应匹配;
  2. 目标是最大化满足nums1[i] > nums2[i]的索引数量,本质是用最优的匹配策略实现收益最大化;
  3. 直接暴力枚举所有排列会产生极高的时间复杂度,无法高效处理较大数据量,因此需要选择更优的算法方案。

结合问题特征,贪心算法+双指针是适配该场景的最优解:贪心策略用于保证每一步选择都能获取当前最优收益,双指针用于高效遍历匹配元素,整体算法可以在线性遍历结合排序的基础上完成计算。

算法思路

核心策略

采用贪心匹配原则:用nums1最小的可用大数去匹配nums2中对应元素,无法满足大小关系时,用nums1中最小的数去填充,最大化有效匹配数量的同时,减少优质元素的浪费。

具体步骤

  1. 数组预处理
    • nums1执行升序排序,方便通过双指针快速获取当前最大/最小可用元素;
    • nums2构建(值, 原索引)的键值对数组,再对该数组执行升序排序。保留原索引是为了保证最终结果能对应到题目要求的原始位置。
  2. 双指针初始化
    定义左指针left指向排序后nums1的起始位置(最小值),右指针right指向排序后nums1的末尾位置(最大值)。
  3. 逆序遍历匹配
    从大到小遍历处理后的nums2数组,依次判断当前元素:
    • nums1的当前最大值大于nums2的当前元素,将该最大值填入结果数组的对应原始索引,右指针左移;
    • 若不满足大小关系,说明当前最大元素也无法形成优势,改用nums1的当前最小值填充,左指针右移。
  4. 输出结果
    遍历完成后,结果数组即为满足条件的nums1最优排列。

C++ 实现代码

#include<vector>#include<algorithm>usingnamespacestd;classSolution{public:vector<int>advantageCount(vector<int>&nums1,vector<int>&nums2){// 获取数组长度intn=nums1.size();// 初始化结果数组,长度与输入数组一致vector<int>res(n,0);// 存储nums2的(值, 原索引)对,保留原始位置信息vector<pair<int,int>>nums2_temp;for(inti=0;i<n;++i){nums2_temp.emplace_back(nums2[i],i);}// 对nums1升序排序sort(nums1.begin(),nums1.end());// 对nums2的键值对数组按值升序排序sort(nums2_temp.begin(),nums2_temp.end());// 双指针初始化:left指向nums1最小值,right指向nums1最大值intleft=0;intright=n-1;// 逆序遍历排序后的nums2_temp,从大元素开始匹配for(inti=n-1;i>=0;--i){intval=nums2_temp[i].first;// nums2当前元素值intindex=nums2_temp[i].second;// 该元素在原数组中的索引// 贪心选择:能用大值匹配就用大值,否则用小值填充if(val<nums1[right]){res[index]=nums1[right];--right;}else{res[index]=nums1[left];++left;}}returnres;}};

复杂度分析

时间复杂度

算法主要耗时操作为排序操作:

  • nums1排序的时间复杂度为O(nlog⁡n)O(n\log n)O(nlogn)
  • nums2键值对数组排序的时间复杂度为O(nlog⁡n)O(n\log n)O(nlogn)
  • 后续双指针遍历为线性操作,时间复杂度为O(n)O(n)O(n)

整体时间复杂度为O(nlog⁡n)O(n\log n)O(nlogn),在数据量较大时仍能保持高效运行。

空间复杂度

  • 额外开辟了存储nums2键值对的数组nums2_temp和结果数组res,两者空间开销均为O(n)O(n)O(n)
  • 排序过程中递归调用栈的空间开销为O(log⁡n)O(\log n)O(logn),可忽略不计。

整体空间复杂度为O(n)O(n)O(n),属于线性空间开销。

算法验证与适用场景

该算法通过贪心策略保证了每一步匹配的最优性,双指针遍历避免了重复判断,能够稳定得到优势最大化的排列。适用于题目给定的所有常规场景,无特殊数据边界限制,在力扣对应题目中可通过全部测试用例。


总结

  1. 本题核心解法为贪心算法+双指针,通过排序预处理和逆序匹配实现最优解;
  2. 算法时间复杂度为O(nlog⁡n)O(n\log n)O(nlogn),空间复杂度为O(n)O(n)O(n),兼顾了时间效率与实现简洁性;
  3. 保留原数组索引是解题关键,确保排列结果能对应到题目要求的原始位置。
版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/4/10 19:39:46

基于深度学习YOLOv11的传送带缺陷识别检测系统(YOLOv11+YOLO数据集+UI界面+登录注册界面+Python项目源码+模型)

一、项目介绍 本文基于深度学习目标检测算法YOLOv11&#xff0c;设计并实现了一套传送带缺陷识别检测系统。系统针对传送带表面常见的四类缺陷&#xff08;堵塞、裂缝、异物、孔洞&#xff09;进行自动化检测&#xff0c;采用改进的YOLOv11模型&#xff0c;结合1860张训练图像…

作者头像 李华
网站建设 2026/4/16 16:42:59

基于深度学习YOLOv12的表情识别检测系统(YOLOv12+YOLO数据集+UI界面+登录注册界面+Python项目源码+模型)

一、项目介绍 本文提出了一种基于深度学习YOLOv12的表情识别检测系统&#xff0c;能够实时检测并分类7种基本表情&#xff08;愤怒、厌恶、恐惧、快乐、中性、悲伤、惊讶&#xff09;。系统采用改进的YOLOv12算法&#xff0c;结合高质量YOLO格式表情数据集&#xff08;训练集44…

作者头像 李华
网站建设 2026/4/18 3:32:41

干货来了:专科生专属AI论文平台 —— 千笔写作工具

你是否曾为论文选题发愁&#xff0c;绞尽脑汁却找不到方向&#xff1f;是否在写到一半时突然卡壳&#xff0c;面对空白文档无从下手&#xff1f;又或是反复修改仍不满意&#xff0c;查重率和格式问题让人焦头烂额&#xff1f;专科生的论文之路本就充满挑战&#xff0c;而千笔AI…

作者头像 李华
网站建设 2026/4/18 3:27:15

个人主页(聚合链接)

个人 主页&#xff1a;https://taplink.cc/chunyu 备用 网址&#xff1a;https://vlink.cc/chunyucode

作者头像 李华
网站建设 2026/4/15 15:34:14

基于深度学习YOLOv12的传送带缺陷识别检测系统(YOLOv12+YOLO数据集+UI界面+登录注册界面+Python项目源码+模型)

一、项目介绍 本文基于YOLOv12深度学习算法&#xff0c;设计并实现了一种高效的传送带缺陷识别检测系统。系统针对传送带表面常见的四类缺陷&#xff08;堵塞、裂缝、异物、孔洞&#xff09;进行自动化检测&#xff0c;通过构建包含1860张训练图像、318张验证图像和167张测试图…

作者头像 李华