• 基础逻辑-分类讨论


    比赛:SDKD 2020 Autumn Training Series C2 1st Round

    题目出处:cf #646 CodeForces - 1363A

    题目大意:

    给定n个数字,然后从中选择x个数字,使得x个数字的和为奇数。询问该种情况是否可能

    解析:

    1、我的思路:

    由于:奇数+奇数=偶数,奇数+偶数=奇数,偶数+偶数=偶数,那么我们可以知道,x个数字如果能够和为奇数,那么在x数字中一定有奇数个奇数以及不知道多少个偶数。

    根据上述的思路,我们枚举所有可能的奇数的个数,然后通过x得到需要的偶数的个数。之后根据已有偶数个数是否能够满足所需偶数个数来确定结果。

    当然,这里仍然需要注意一个要点。由于奇数+奇数=偶数(即偶数个奇数和为偶数),那么是否可能存在:某一次枚举过程中,由于偶数个数不能满足,需要使用成对的奇数来代替偶数的情况呢?

    我们假设这种情况是存在的,那么我们所需要的用来替代偶数的成对奇数,一定是有偶数个奇数的。因为只有偶数个奇数才能充当偶数来使用。这时,我们发现,最终结果仍然是由奇数个奇数组成的。

    所以上述的额外情况并不需要特殊处理,它已经被包含到了遍历的过程中。

    代码如下:

    const int maxn = 1000+100;
    int a[maxn];
    int main(){
        //freopen("in.txt","r",stdin);
        int num;
        cin>>num;
        while(num--){
            int n,x;
            scanf("%d%d",&n,&x);
            int odd  = 0;
            int even = 0;
            for(int i=0;i<n;i++){
                scanf("%d",&a[i]);
                if(a[i]&1)odd++;
                else even++;
            }
            //开始处理一般情况
            bool ok = false;
            int odd_num = 1;
            while(odd_num<=odd && odd_num<=x){
                //这里的一个坑就是odd的选用个数不仅不能超过odd总个数
                //也不能超过所要求选取的总个数
                if(x - odd_num <= even){
                    ok=true;break;
                }
                odd_num+=2;
            }
            if(ok){
                cout<<"Yes"<<endl;
            }else{
                cout<<"No"<<endl;
            }
        }
        return 0;
    }
    

    2、其他思路:

    其实这种题目本身考量的就是对多种情形的分类讨论

    这里也就不在多讨论。不过值得一提的是,经过对多个同学的分析,我发现这道水题一般写的快的学生,
    大部分都是在进行单纯的分类讨论。针对上述的第一种思路,并没有多少人这样写。而写得稍慢的学生却
    出现了有提交该思路代码的现象。

    OK

  • 相关阅读:
    大厂面试高频Redis,记不住的多操作几次吧
    自动化测试系列之jenkins配置搭建环境
    关于linux服务器的磁盘监控的相关知识
    前端常见一些安全问题及解决方案
    如何使用PM2部署前端项目
    vuex状态管理器本地持久化
    关于在Vue中Typescript的写法
    websocket快速重连机制
    如何使用selenium打开多个浏览器
    运维人员踩坑记录之netplan遇坑,配置临时IP巧妙解决
  • 原文地址:https://www.cnblogs.com/savennist/p/13746891.html
Copyright © 2020-2023  润新知