【CodeForces训练记录】Codeforces Round 1016 (Div. 3)

训练情况

赛后反思

经典操作之枚举因数判质数不特判 \(1\),怒吃两发罚时

A题

直接瞪眼看样例,直接猜奇偶分类讨论,一分钟秒了

点击查看代码
#include <bits/stdc++.h>
// #define int long long
#define endl '\n'

using namespace std;

void solve(){
    int x; cin>>x;
    if(x&1) cout<<"YES"<<endl;
    else cout<<"NO"<<endl;
} 

signed main(){
	ios::sync_with_stdio(false);
	cin.tie(0),cout.tie(0);
    int T; cin>>T; while(T--)
    solve();
    return 0;
}

B题

这题显然剩下只有一个数是最优的,因为 \(\frac{x}{x} = 1\),但是不能剩下零,所以我们考虑先删非零的数,留下一个非零的数,接下来就是考虑零的问题,如果零在那个数的右边也不行,所以需要把右边的零也删了,所以答案是非零个数-1+后导零的数量

点击查看代码
#include <bits/stdc++.h>
// #define int long long
#define endl '\n'

using namespace std;

void solve(){
    string s; cin>>s;
    int cnt = 0;
    for(int i = 0;i<s.size();i++) if(s[i] != '0') cnt++;
    int add = 0,pos = s.size() - 1;
    for(int i = s.size() - 1;~i;i--){
        if(s[i] != '0'){
            pos = i;
            break;
        }
    }
    add = s.size() - pos - 1;
    // cout<<add<<endl;
    cout<<cnt-1+add<<endl;
}

signed main(){
	ios::sync_with_stdio(false);
	cin.tie(0),cout.tie(0);
    int T; cin>>T; while(T--)
    solve();
    return 0;
}

C题

字符串拼接我们可以等效成 \(\times 10^{p}\),比如 22 3,就是 \(22 + 22 \times 10^{2} + 22 \times 10^{4}\),质数显然是除了 \(1\) 和自身没有其他因数,我们先不考虑 \(x=1\) 的情况,对于 \(k>1\) 时上述式子一定能提出来一个公因数 \(x(x \neq 1)\),所以一定不是质数,\(k=1\) 直接判断那个数是否是质数即可,复杂度是 \(O(logV)\) 的,接下来我们特殊考虑 \(x=1\) 的情况,由于七个一值域很小,按照题目描述拼接判断质数即可

点击查看代码
#include <bits/stdc++.h>
#define int long long
#define endl '\n'

using namespace std;

void solve(){
    int x,k; cin>>x>>k;
    bool flag = true;
    if(x == 1){
        int ck = 0;
        for(int i = 1;i<=k;i++) ck = ck*10 + 1;
        if(ck==1) flag = false;
        for(int i = 2;i<=sqrt(ck);i++){
            if(ck%i==0){
                flag = false;
                break;
            }
        }
        if(flag) cout<<"YES"<<endl;
        else cout<<"NO"<<endl;
        return;
    }
    for(int i = 2;i<=sqrt(x);i++){
        if(x%i==0){
            flag = false;
            break;
        }
    }
    if(!flag) cout<<"NO"<<endl;
    else if(k>1) cout<<"NO"<<endl;
    else cout<<"YES"<<endl;
}

signed main(){
	ios::sync_with_stdio(false);
	cin.tie(0),cout.tie(0);
    int T; cin>>T; while(T--)
    solve();
    return 0;
}

E题

触发关键词最小值最大,直接考虑二分答案,我们二分 \(\operatorname{mex}\),对于 \(\operatorname{mex} = x\) 情况,我们可以推出来需要分成几段,和题目给出的 \(k\) 比较就是二分单调性了,求区间数我们可以遍历数组,如果当前所选的区间 \(\operatorname{mex}\) 满足了就去找下一个区间,维护不同数出现的个数和某个数是否出现过即可

点击查看代码
#include <bits/stdc++.h>
#define int long long
#define endl '\n'

using namespace std;

const int N = 2e5 + 3;

int n,k;
int a[N];

bool pd(int x){
    int cnt = 0;
    int ans = 0;
    vector<bool> v(N,0);
    for(int i = 1;i<=n;i++){
        if(a[i] < x && !v[a[i]]) v[a[i]] = 1,cnt++;
        // cout<<i<<" "<<cnt<<endl;
        if(cnt == x) v.assign(N,0),cnt=0,ans++;
    }
    // cout<<k<<" "<<x<<" "<<ans<<endl;
    return ans >= k;
}
;
void solve(){
    cin>>n>>k;
    for(int i = 1;i<=n;i++) cin>>a[i];
    int l = 0,r = 1e9 + 1,m;
    while(l<r){
        m = l + r + 1 >> 1;
        if(pd(m)) l = m;
        else r = m-1;
    }
    cout<<l<<endl;
}

signed main(){
	ios::sync_with_stdio(false);
	cin.tie(0),cout.tie(0);
    int T; cin>>T; while(T--)
    solve();
    return 0;
}
posted @ 2025-04-09 00:52  MNNUACM_2024ZY  阅读(102)  评论(0)    收藏  举报