接着剤の精進日記

競プロでの精進や研究に関係したことを書いていきます。

AtCoder Beginner Contest 148 (ABC148)

算数苦手芸人
みんな算数問題強すぎないか
f:id:tkm-kyudo:20191223120122p:plain

A - Round One

何でもできそう
配列に入れてチェックした
a xor bで出来るの天才ですね…
提出コード

int main(){
    cin.tie(0);
    ios::sync_with_stdio(false);
    vector<int> num(4);
    int a, b;
    cin >> a >> b;
    num[a]++, num[b]++;
    for(int i=1;i<=3;i++){
        if(num[i] == 0){
            cout << i << endl;
            return 0;
        }
    }
}

B - Strings with the Same Length

S[i]T[i]を出力していくだけ
提出コード

int main(){
    cin.tie(0);
    ios::sync_with_stdio(false);
    int N;
    cin >> N;
    string S, T;
    cin >> S >> T;
    REP(i, N) cout << S[i] << T[i];
    cout << endl;
}

C - Snack

最小公倍数を出力
最小公倍数を知らなくてもA × Bまで見れば十分なのでループでも行ける
提出コード

ll gcd(ll x, ll y){
  return y ? gcd(y, x%y) : x;
}

ll lcm( ll m, ll n ){
    if ( ( 0 == m ) || ( 0 == n ) ) return 0;
    return ((m / gcd(m, n)) * n);
}

int main(){
    cin.tie(0);
    ios::sync_with_stdio(false);
    int A, B;
    cin >> A >> B;
    cout << lcm(A, B) << endl;
}

D - Brick Break

まず1がない場合は駄目
それ以外は、左から順に見ていって1があればそれを残し、2を探す…というのを続けていけばいい
本番中は頭が着いていなくて、idxを持ってにぶたんしてた
本番で通した時みんなめちゃくちゃ早くて天才か?って言ってた(線形で出来ますね)
提出コード

vector<vector<int>> idx(202020);

int main(){
    cin.tie(0);
    ios::sync_with_stdio(false);
    int N;
    cin >> N;
    REP(i,N){
        int num;
        cin >> num;
        idx[num].push_back(i);
    }

    int cur = 0;
    int cnt = 0;
    while(cur < N){
        auto itr = lower_bound(idx[cnt+1].begin(), idx[cnt+1].end(), cur);
        if(itr == idx[cnt+1].end()){
            if(cnt == 0){
                cout << -1 << endl;
                return 0;
            }
            break;
        }
        cnt++;
        cur = *itr;
    }

    cout << N - cnt << endl;
}

E - Double Factorial

算数問題(中受)
本番中は10, 100, ...の倍数考えて包除とかやろうとしてた
よく考えると10は素因数2と5を持つのでN!が持つ素因数2と5の最小が答え
実際には素因数2よりも素因数5のほうが明らかに小さいので、5だけ数えればいい
提出コード

int main(){
    cin.tie(0);
    ios::sync_with_stdio(false);
    ll N;
    cin >> N;

    if(N % 2 == 1 || N < 10){
        cout << 0 << endl;
        return 0;
    }
    ll ans = 0;
    ll base = 10;
    while(N >= base){
        ans += N / base;
        base *= 5;
    }
    cout << ans << endl;
}

おわりに

算数問題出る時大体冷えてる気がする
Educational 算数 Contestはまだですか?
焦ってたとは言え、素因数で見るのは典型だと思うので通せないのが悪いね、しょうがない