当前位置: 首页 > news >正文

【C++堆(优先队列)】2233. K 次增加后的最大乘积|1685

本文涉及知识点

C++堆(优先队列)
贪心(决策包容性)

LeetCode 2233. K 次增加后的最大乘积

给你一个非负整数数组 nums 和一个整数 k 。每次操作,你可以选择 nums 中 任一 元素并将它 增加 1 。
请你返回 至多 k 次操作后,能得到的 nums的 最大乘积 。由于答案可能很大,请你将答案对 109 + 7 取余后返回。
示例 1:
输入:nums = [0,4], k = 5
输出:20
解释:将第一个数增加 5 次。
得到 nums = [5, 4] ,乘积为 5 * 4 = 20 。
可以证明 20 是能得到的最大乘积,所以我们返回 20 。
存在其他增加 nums 的方法,也能得到最大乘积。
示例 2:

输入:nums = [6,3,3,2], k = 2
输出:216
解释:将第二个数增加 1 次,将第四个数增加 1 次。
得到 nums = [6, 4, 3, 3] ,乘积为 6 * 4 * 3 * 3 = 216 。
可以证明 216 是能得到的最大乘积,所以我们返回 216 。
存在其他增加 nums 的方法,也能得到最大乘积。
提示:
1 <= nums.length, k <= 105
0 <= nums[i] <= 106

堆(优先队列)

贪心:k次操作,每次选择最小的数+1。操作后按升序排序res。下面来证明正确性:
某方案后,升序排序后结果是res1。如果方案不同,至少存在一个
res1[i1] < res[i1] res1[i2] > res[i2] i1 < i2。 res1[i1] < res[i1] <= res[i2] < res1[i2]。
将res1[i1]++ res1[i2]-- ,结果变大。++变成 (res1[i1]+1)/res1[i1] ; --变成 res1[i2]/(res1[i2]-1)
两者相除:y= (res1[i1]+1)*(res1[i2]-1)/res1[i1]res1[i2]
(res1[i1]res1[i2] +(res1[i2]-res1[i1])-1)/res1[i1]res1[i2]
由于res1[i2] > res1[i1] 故 (res1[i2]-res1[i1])-1) >=0,即y >= 1,即变大或不变。

代码

核心代码

template<int MOD = 1000000007>
class C1097Int
{
public:C1097Int(long long llData = 0) :m_iData(llData% MOD){}C1097Int  operator+(const C1097Int& o)const{return C1097Int(((long long)m_iData + o.m_iData) % MOD);}C1097Int& operator+=(const C1097Int& o){m_iData = ((long long)m_iData + o.m_iData) % MOD;return *this;}C1097Int& operator-=(const C1097Int& o){m_iData = (m_iData + MOD - o.m_iData) % MOD;return *this;}C1097Int  operator-(const C1097Int& o){return C1097Int((m_iData + MOD - o.m_iData) % MOD);}C1097Int  operator*(const C1097Int& o)const{return((long long)m_iData * o.m_iData) % MOD;}C1097Int& operator*=(const C1097Int& o){m_iData = ((long long)m_iData * o.m_iData) % MOD;return *this;}C1097Int  operator/(const C1097Int& o)const{return *this * o.PowNegative1();}C1097Int& operator/=(const C1097Int& o){*this /= o.PowNegative1();return *this;}bool operator==(const C1097Int& o)const{return m_iData == o.m_iData;}bool operator<(const C1097Int& o)const{return m_iData < o.m_iData;}C1097Int pow(long long n)const{C1097Int iRet = 1, iCur = *this;while (n){if (n & 1){iRet *= iCur;}iCur *= iCur;n >>= 1;}return iRet;}C1097Int PowNegative1()const{return pow(MOD - 2);}int ToInt()const{return m_iData;}
private:int m_iData = 0;;
};
class Solution {public:int maximumProduct(vector<int>& nums, int k) {std::priority_queue<int,vector<int>,greater<>> minHeap(nums.begin(),nums.end());while (k--) {auto cur = minHeap.top()+1;minHeap.pop();minHeap.emplace(cur);}C1097Int<> ret = 1;while (minHeap.size()) {ret *= minHeap.top();minHeap.pop();}return ret.ToInt();}};

单元测试

vector<int> nums;int k;TEST_METHOD(TestMethod11){nums = { 0, 4 }, k = 5;auto res = Solution().maximumProduct(nums, k);AssertEx(20, res);}TEST_METHOD(TestMethod12){nums = { 6,3,3,2 }, k =2;auto res = Solution().maximumProduct(nums, k);AssertEx(216, res);}

扩展阅读

我想对大家说的话
工作中遇到的问题,可以按类别查阅鄙人的算法文章,请点击《算法与数据汇总》。
学习算法:按章节学习《喜缺全书算法册》,大量的题目和测试用例,打包下载。重视操作
有效学习:明确的目标 及时的反馈 拉伸区(难度合适) 专注
闻缺陷则喜(喜缺)是一个美好的愿望,早发现问题,早修改问题,给老板节约钱。
子墨子言之:事无终始,无务多业。也就是我们常说的专业的人做专业的事。
如果程序是一条龙,那算法就是他的是睛
失败+反思=成功 成功+反思=成功

视频课程

先学简单的课程,请移步CSDN学院,听白银讲师(也就是鄙人)的讲解。
https://edu.csdn.net/course/detail/38771
如何你想快速形成战斗了,为老板分忧,请学习C#入职培训、C++入职培训等课程
https://edu.csdn.net/lecturer/6176

测试环境

操作系统:win7 开发环境: VS2019 C++17
或者 操作系统:win10 开发环境: VS2022 C++17
如无特殊说明,本算法用**C++**实现。


http://www.mrgr.cn/news/45085.html

相关文章:

  • 深度优先搜索与并查集
  • Windows VSCode 配置 Java 环境 (Maven)
  • Steam Deck掌机可装“黑苹果” 开发者成功安装macOS 15 Sequoia
  • 织物布匹疵点检测数据集,布匹缺陷检测数据集 标注工具:LabelImg 数量:已标注1084张(5类);未标注:2000余张
  • Vue 3 中实现懒加载功能
  • 数据结构——优先级队列(堆)
  • python画图|曲线动态输出基础教程
  • 什么是安全运营中心 SOC?
  • 第三课 Vue中的方法的定义及事件绑定指令
  • 线性代数入门指南
  • 『网络游戏』制作提示弹窗UI【03】
  • 线性代数入门
  • 正确理解协程
  • 读数据工程之道:设计和构建健壮的数据系统02数据工程师
  • 【星闪开发连载】SLE_UUID_Server和SLE_UUID_Client程序测试
  • 『网络游戏』制作加载进度UI【04】
  • <<迷雾>> 第 9 章 计算机时代的开路先锋 示例电路
  • AI学习指南深度学习篇-生成对抗网络的基本原理
  • SIE将使用AI和机器学习加速游戏开发
  • Python软体中使用NLTK进行文本分析