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

【C++贪心 位运算】B3930 烹饪问题|普及

本文涉及知识点

C++贪心
位运算、状态压缩、枚举子集汇总

B3930 [GESP202312 五级] 烹饪问题

题目描述

N N N 种食材,编号从 0 0 0 N − 1 N-1 N1,其中第 i i i 种食材的美味度为 a i a_i ai

不同食材之间的组合可能产生奇妙的化学反应。具体来说,如果两种食材的美味度分别为 x x x y y y ,那么它们的契合度为 $x\ \text{and}\ y $。

其中, and \text{and} and 运算为按位与运算,需要先将两个运算数转换为二进制,然后在高位补足 ,再逐位进行与运算。例如, 12 12 12 6 6 6 的二进制表示分别为 1100 1100 1100 0110 0110 0110 ,将它们逐位进行与运算,得到 0100 0100 0100 ,转换为十进制得到 4,因此 12 and 6 = 4 12 \text{and} 6 = 4 12and6=4在 C++ 或 Python 中,可以直接使用 & 运算符表示与运算。

现在,请你找到契合度最高的两种食材,并输出它们的契合度。

输入格式

第一行一个整数 N N N,表示食材的种数。

接下来一行 N N N 个用空格隔开的整数,依次为 a 1 , ⋯ , a N a_1,\cdots,a_N a1,,aN,表示各种食材的美味度。

输出格式

输出一行一个整数,表示最高的契合度。

样例 #1

样例输入 #1

3
1 2 3

样例输出 #1

2

样例 #2

样例输入 #2

5
5 6 2 10 13

样例输出 #2

8

提示

样例解释 1

可以编号为 1 , 2 1,2 1,2 的食材之间的契合度为 2 and  3 = 2 2\ \text{and} \ 3=2 2 and 3=2,是所有食材两两之间最高的契合度。

样例解释 2

可以编号为 3 , 4 3,4 3,4 的食材之间的契合度为 10 and  13 = 8 10\ \text{and}\ 13=8 10 and 13=8,是所有食材两两之间最高的契合度。

数据范围

对于 40 % 40\% 40% 的测试点,保证 N ≤ 1 , 000 N \le 1,000 N1,000

对于所有测试点,保证 N ≤ 1 0 6 N \le 10^6 N106 0 ≤ a i ≤ 2 , 147 , 483 , 647 0\le a_i \le 2,147,483,647 0ai2,147,483,647

贪心+试填法

int 共32位,去掉符合位,还是31位。从高到低处理第i位,i = 30 to 0。
如果第i位为1的数字达到2,则删除所有此位为0的数字。如果选择了这些数字,此位一定是0。
如果第i位为1的数字没有或只有一个,则什么都不干。
余下的任意两个数字位与,就是本题答案。
向量删除元素时间复杂度是O(n),如果对顺序没有要求,和最后一个元素交换后删除,这样时间复杂度是:O(1)。

代码

核心代码

#include <iostream>
#include <sstream>
#include <vector>
#include<map>
#include<unordered_map>
#include<set>
#include<unordered_set>
#include<string>
#include<algorithm>
#include<functional>
#include<queue>
#include <stack>
#include<iomanip>
#include<numeric>
#include <math.h>#include <bitset>
using namespace std;class Solution {
public:int MaxS(vector<int>& nums) {for (int i = 30; i >= 0; i--) {vector<int> tmp;for (const auto& n : nums) {if (n & (1 << i)) { tmp.emplace_back(n); }}if (tmp.size() >= 2) { tmp.swap(nums); }}if (0 == nums.size()) { return 0; }return nums.front() & nums.back();}
};
int main() {
#ifdef _DEBUGfreopen("a.in", "r", stdin);
#endif // DEBUGint n;scanf("%d", &n);Solution slu;vector<int> nums;while (n--) {int h;	scanf("%d", &h);nums.emplace_back(h);		}int res = slu.MaxS(nums);printf("%d\r\n", res);return 0;
}

单元测试

	TEST_METHOD(TestMethod1){nums = { 1, 2, 3 };auto res = Solution().MaxS(nums);AssertEx(2, res);}TEST_METHOD(TestMethod11){nums = { 5, 6, 2 ,10 ,13 };auto res = Solution().MaxS(nums);AssertEx(8, 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++**实现。

相关文章:

  • Day20打卡-奇异值SVD分解
  • 2025年大模型RAG技术的实践总结
  • 解释器和基于规则的系统比较
  • 历史数据分析——北部湾港
  • (2025)图文解锁RAG从原理到实操
  • 当冲压焊接遇上Canopen到Profinet协议转换网关
  • 【XCP实战】AUTOSAR架构下XCP DAQ功能配置实现
  • 代码随想录算法训练营第三十七天
  • 学习黑客5 分钟深入浅出理解Linux Logs [特殊字符]
  • MD5 值是什么?为什么文件需要检验 MD5?
  • 手机银行怎么打印流水账单(已解决)
  • LintCode第485题-生成给定大小的数组,第220题-冰雹猜想,第235题-分解质因数
  • 便签软件哪个好用?2025年桌面记事本便签软件推荐大全
  • ProfiNet转MODBUS模块构建西门子PLC与RTU仪表通讯连接方案
  • 考研408《计算机组成原理》复习笔记,第三章数值数据的表示和运算(定点数篇)
  • CMake 入门实践
  • jflash下载时出现 Could not read unit serial number! 的解决方法
  • SierraNet M1288网络损伤功能显著助力GPU互联网络的测试验证,包含包喷洒,LLR等复杂特性的验证测试
  • Python中的事件循环是什么?事件是怎么个事件?循环是怎么个循环
  • 【C++】string类(一)构造、重载、容量操作、访问与遍历(迭代器、范围for)、练习
  • “海豚音”依旧,玛丽亚·凯莉本周来沪开唱
  • 中山大学人类学系原系主任冯家骏逝世,享年95岁
  • 观察|天空之外的战场:官方叙事、新闻与社交平台中的印巴冲突
  • 4月证券私募产品备案量创23个月新高,股票策略占比超六成
  • 匈牙利外长称匈方已驱逐两名乌克兰外交官
  • 前4个月我国货物贸易进出口同比增长2.4%,增速较一季度加快1.1个百分点