• 首页 首页 icon
  • 工具库 工具库 icon
    • IP查询 IP查询 icon
  • 内容库 内容库 icon
    • 快讯库 快讯库 icon
    • 精品库 精品库 icon
    • 问答库 问答库 icon
  • 更多 更多 icon
    • 服务条款 服务条款 icon

HAUT1227 Flowers贪心

武飞扬头像
小胡同的诗
帮助1

题目链接haut1227

题面

学新通

解题思路

贪心

这个问题的第一个关键点在于要发现:组成混合颜色的方案一定要优先于组成纯色的方案。因为组成混色方案更具鲁棒性。在相同资源下,组成三束分别不同颜色的花束一定也可以将其改成三束混合颜色的花束;而在小于三束混色花束的资源下却无法组成任何一束花。于是,我们大胆认为前者方案优于后者。

第二个关键点在于要发现:构成最大方案数的核心部分就是混合颜色的花束数量,因为当无法构成混合颜色花束时,问题就相当简单了,直接计算各自的纯色花束即可。而构成混合颜色花束数量取决于三种颜色中,花朵数量最小的那堆,所以我们先处理那堆最小的,处理完毕后再处理剩下的纯色的方案。

根据关键点二,我们容易形成一种错误的算法,就是把所有『最小堆』中的花朵全部都拿来构成混合颜色的花束,基于这个算法我们可以给出反例:2 7 7,这个样例正确答案应该是 5 ,也就是一个混合颜色花束加四束纯色花束,而不是上述算法所计算的 4 。

问题出在哪呢?这样的只形成局部最优而非全局最优的错误点不由得让人想直接去搜索,但是怎么搜索呢?根据关键点一的观点,我们可以考虑搜索『最小堆』的混合花束数量(实际上枚举就行了)。但是如果『最小堆』的花朵数量很多,那么我们这块的复杂度是相当爆炸的。我们发现在这种搜索策略下,『最小堆』中花朵的状态仅有三种:用于纯色、用于混色、闲置。而根据关键点一,当它能用于纯色时我们显然可以将其用混色替代。于是,状态就变成两种:混色、闲置。显然,当闲置了三个花朵我们肯定能将其至少组成一个纯色花束(其实还是可以转成混合颜色花束)。于是,这堆中,闲置花朵数量仅需考虑 0    1    2 0 \; 1 \; 2 012 ,最后取三种方案中最大的即可。

最后,我们再考虑『最大堆』『次大堆』剩下的花朵组成纯色花束。事实上,我们优先考虑混合颜色花束相当于是在切断三种颜色之间的相互约束,使得问题更简单而已。

可能我们还有个疑问,就是『最小堆』中最优情况下,那些闲置的花朵会不会有机会和其他颜色的花朵再构成混合花束?答案是否定的。因为我们枚举的这个最优情况实际上就是在最大程度利用其他两堆,使其能够减少闲置,更多地利用起来形成纯色花束,也就是说,最优情况下,其他两堆必然至少有一堆剩下的花朵全部都能构成纯色花束。

时间复杂度 O ( 1 ) O(1) O(1)空间复杂度 O ( 1 ) O(1) O(1)


实现代码

贪心

#include <bits/stdc  .h>

using namespace std;

int f(int r, int g, int b) {
    int m = min({r, g, b}), k = 0;
    for (int i = 0; i <= min(m, 2); i  ) {
        k = max(k, m-i   (r-m i)/3   (g-m i)/3   (b-m i)/3); //混合颜色   纯色
    }
    return k;
}

int main() {
    int red, green, blue;
    cin >> red >> green >> blue;
    cout << f(red, green, blue) << endl;
    return 0;
}

这篇好文章是转载于:学新通技术网

  • 版权申明: 本站部分内容来自互联网,仅供学习及演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,请提供相关证据及您的身份证明,我们将在收到邮件后48小时内删除。
  • 本站站名: 学新通技术网
  • 本文地址: /boutique/detail/tanhgehhab
系列文章
更多 icon
同类精品
更多 icon
继续加载