B3930 [GESP202312 五级] 烹饪问题

B3930 GESP202312 五级 烹饪问题

题目背景

对应的选择、判断题:https://ti.luogu.com.cn/problemset/1137

题目描述

有 N N N 种食材,编号从 1 1 1 至 N N N,其中第 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 12 and 6=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

可以编号为 2 , 3 2,3 2,3 的食材之间的契合度为 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 N≤1,000;

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

cpp 复制代码
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;

ll a[1000010];  // 存储所有美味度
ll n;

int main() {
    ios::sync_with_stdio(0);
    cin.tie(0);
    cout.tie(0);

    cin >> n;
    for (ll i = 1; i <= n; i++) {
        cin >> a[i];
    }

    ll ans = 0;  // 当前能取到的最大值

    /*
     * 从高位到低位贪心
     * 一共 30 位
     */
    for (int bit = 30; bit >= 0; bit--) {

        /*
         * 尝试把当前这一位"强行设为 1"
         * now 表示:ans 的基础上,新增这一位
         */
        ll now = ans | (1LL << bit);

        int cnt = 0;  // 统计有多少个数支持这个 now

        /*
         * 检查所有数
         * (a[i] & now) == now
         * 含义:
         * - a[i] 在 now 为 1 的位上,也必须为 1
         * - 即:a[i] 包含 now 的所有 1
         */
        for (int i = 1; i <= n; i++) {
            if ((a[i] & now) == now) {
                cnt++;
            }
        }

        /*
         * 如果至少有 2 个数满足
         * 说明可以把这一位保留下来
         */
        if (cnt >= 2) {
            ans = now;
        }
    }

    cout << ans << endl;
    return 0;
}
相关推荐
写代码写到手抽筋2 小时前
5G上行DCI字段判定:端口 流数 PMI选择详解
java·算法·5g
xieliyu.2 小时前
Java算法精讲:双指针(二)
java·开发语言·算法
苏宸啊2 小时前
IPC管道
linux·c++
何以解忧,唯有..2 小时前
Python包管理工具pip:从入门到精通
开发语言·python·pip
BestOrNothing_20152 小时前
ROS2 话题通信实战:消息对象、Publisher 发布器与 Subscriber 订阅器保姆级教程
c++·ros2·subscriber·publisher·话题通信
wayz112 小时前
Momentum:PSL(心理线指标)技术指标详解
算法·金融·数据分析·量化交易·特征工程
雪的季节3 小时前
RabbitMQ详解
开发语言
努力学习_小白3 小时前
ResNeXt-50——学习记录
pytorch·深度学习·学习
8Qi83 小时前
LeetCode 213:打家劫舍 II(House Robber II)—— 题解 ✅
算法·leetcode·职场和发展·动态规划
ice8130331813 小时前
【Python】Matplotlib折线图绘制
开发语言·python·matplotlib