• Codeforces Round #651 (Div. 2)A、B、C、D、E


    题目
    A题意:1到n中任选两个不同的数,gcd最大为大少。
    解法:假设最大公约数为g,两个数不同所以两个数分别为g,2g.所以g=[(frac{n}{2})]

    void solve(){
        int n ;
        cin >> n ;
        cout << n/2 << endl;
    }
    

    B题意:给出一个2n数组a,从a数组选出2(n-1),每次取两个数,其和加入b数组,使b数组构成一个n-1长且gcd(b1,b2,...,bn)>1,输出n-1对数在a数组的下标。
    解法:gcd>1,考虑b数组全为偶数必然满足条件,把a数组分成奇偶两组,奇数两两配对,偶数两两配对,一定可以至少选出n-1对数的和为偶数。

    void solve(){
        int n ;
        cin >> n ;
        vector<int>j , o;
        rep(i , 1 , n*2){
            cin >> a[i];
            if(a[i]%2==1){
                j.pb(i);
            }else{
                o.pb(i);
            }
        }
        vector<pii>v;
        for(int i = 1 ; i <= size(j)-1 ; i+=2){
            v.pb(mp(j[i] , j[i-1]));
        }
        for(int i = 1 ; i <= size(o)-1 ; i+=2){
            v.pb(mp(o[i] , o[i-1]));
        }
        for(int i = 0 ; i < n-1 ; i++){
            cout << v[i].fi << " " << v[i].se << endl;
        }
     
    }
    

    C题意:给出一个n,两个轮流进行以下两个操作中的一个最后不能操作的一方为败方,问谁为胜方。
    1、n除以一个奇数因子
    2、n(n>1)减去1
    解法:1、如果为奇数先手赢。直接全拿走
    2、质因子2只有1个,且其他质因子大于1个,则先手赢。策略:先手拿其他质因子数剩下一个,后手处于必败态
    3、质因子2多于1个,且有其质他因子,则先手赢。策略:先手拿光其他质因子(一定为奇数),将大于2的偶数必败态转给了对手
    4、2为先手赢
    其他情况为后手胜。

    void solve(){
        int n ;
        cin >> n ;
        if(n == 1){
            cout << "FastestFinger" << endl;
        }else if(n == 2){
            cout << "Ashishgup" << endl;
        }else{
            if(n % 2 == 1){
                cout << "Ashishgup" << endl;
            }else{
                int cnt = 0 ;
                while(n%2==0){
                    n/=2;
                    cnt++;
                }
                if(n == 1){//只有2质因子
                    cout << "FastestFinger" << endl;
                }else{
                    if(cnt == 1 && !is_prime(n)){//2质因子只有1个,其他质因子有多于1个
                        cout << "Ashishgup" << endl;
                    }else if(cnt > 1){//质因子2多于1个,且有其他质因子
                        cout << "Ashishgup" << endl;
                    }else{
                        cout << "FastestFinger" << endl;
                    }
                }
            }
        }
    }
    

    D题意:给出一个n个数的数组,从中挑选k个数,形成一个新的数组,定义该数组的值为(min(max(s_1,s_3,s_5..., s_2,s_4,s_6...))),问该数组值为最小为多少。
    解法:二分答案+贪心。分两种情况,如果该最小值为奇数贡献,遍历只要符合条件(小于二分枚举值)则加入奇数下标中,下一个数如果有就加入偶数下标,判断一下奇偶数的个数是否满足条件,偶数贡献同理。

    const int maxn = 2e5+9;
    int a[maxn];
    int n , k ;
    int lenj , leno ;
    
    bool check(int x){
        int i = 1 , j = 0 , o = 0 ;
        while(i <= n){
            if(a[i] <= x){
                j++;
                if(i+1 <= n){
                    i += 2 ;
                    o++;
                }else{
                    i++;
                }
            }else{
                i++;
            }
        }
        if(j >= lenj && o >= leno) return true;
        i = 2 , j = 1 , o = 0 ;
        while(i <= n){
            if(a[i] <= x){
                o++;
                if(i+1 <=n){
                    i+=2;
                    j++;
                }else{
                    i++;
                }
            }else{
                i++;
            }
        }
        if(j >= lenj && o >= leno) return true;
        return false;
    }
    
    void solve(){
         cin >> n >> k ;
         lenj = (k+1)/2 , leno = k/2;
         rep(i , 1 , n){
             cin >> a[i];
         }
         int l = 1 , r = 1e9 ;
         while(r > l){
             int mid = (l + r) >> 1;
             if(check(mid)){
                 r = mid ;
             }else{
                 l = mid + 1;
             }
         }
         cout << r << endl;
    }
    

    E题意:给出n长两个字符数组a、b,可以取a数组的任意子序列进行顺时针旋转,sn->s1,s1->s2...。问a字符数组能否转变为b字符数组。
    解法:首先判断a与b中相同字符数量是否相等。不相等则输出-1.
    相同的字符不需要转动,所以旋转序列不选它们,因为所选序列为0101010或1010101.
    10则a数组需要向右移,01b数组需要向左移。

    void solve(){
         int n ;
         cin >> n ;
         scanf("%s%s" , a+1 , b+1);
         int x = 0 , ma = 0 , mi = 0 ;
         rep(i , 1 , n){
             x += a[i] - '0';
             x -= b[i] - '0';
             ma = max(ma , x);//往a需要右移ma位
             mi = min(mi , x);//b需要往左移mi位
         }
         int ans = ma - mi ;
         if(x != 0) ans = -1;
         cout << ans << endl;
    }
    
  • 相关阅读:
    python 远程 部署和运行
    学习笔记——UML类图
    Core Data 多线程操作实战篇
    Core Data系列六——Custom Migration
    Core Data系列五——数据迁移方案
    NSOperation以及NSOperationQueue的使用
    Magical Record设计小谈
    Core Data系列四——多线程设计
    Core Data系列三——基本使用
    Core Data系列二——基础概念
  • 原文地址:https://www.cnblogs.com/nonames/p/13175982.html
Copyright © 2020-2023  润新知