zoukankan      html  css  js  c++  java
  • AtCoder Beginner Contest 185

    AtCoder Beginner Contest 185

    A - ABC Preparation

    Solution

    输出最小值

    #include <iostream>
    #include <algorithm>
    using namespace std;
    
    int main()
    {
        int a1, a2, a3, a4;
        cin >> a1 >> a2 >> a3 >> a4;
        cout << min(min(a1, a2), min(a3, a4)) << endl;
        return 0;
    }
    
    B - Smartphone Addiction

    Solution

    模拟即可

    #include <iostream>
    #include <vector>
    #include <algorithm>
    using namespace std;
    
    int main()
    {
        int n, t, m, cap;
        cin >> n >> m >> t; cap = n;
        bool fl= true, wh = true;
        int lt = 0;
        for(int i = 0; i < m * 2; ++i) {
            int mt; cin >> mt;
            if(wh) {
                n -= mt - lt;
            }
            else {
                n += mt - lt;
            }
            n = min(n, cap);
            if(n <= 0) fl = false;
            wh = !wh;
            lt = mt;
        }
        if(wh) {
            n -= t - lt;
        }
        else {
            n += t - lt;
        }
        n = min(n, cap);
        if(n <= 0) fl = false;
        cout << (fl ? "Yes" : "No") << endl;
        return 0;
    }
    
    C - Duodecim Ferra

    Solution

    裁成12段,需要11个裁点,长为L裁点有L-1个,所以答案为(C_{L-1}^{11}),因为中间结果会long long,所以用递推式计算:(C_n^m=C_{n-1}^m+C_{n-1}^{m-1})

    #include <iostream>
    #include <algorithm>
    using namespace std;
    
    typedef long long ll;
    
    ll c[222][222];
    
    int main()
    {
        ll l;
        cin >> l;
        l--;
        for(int i = 0; i <= l; ++i) c[i][0] = c[i][i] = 1, c[i][1] = i;
        for(int i = 1; i <= l; ++i) {
            for(int j = 2; j < i; ++j) {
                c[i][j] = c[i - 1][j - 1] + c[i - 1][j];
            }
        }
        cout << c[l][11] << endl;
        return 0;
    }
    
    D - Stamp

    Solution

    找到最小的白色区间,即为最大可用stamp width,然后对每段计算需要几个stamp求和即可。

    #include <iostream>
    #include <vector>
    #include <algorithm>
    using namespace std;
    
    const int maxn = 211111;
    
    int a[maxn];
    
    int main()
    {
        int n, m; cin >> n >> m;
        vector<int> dis;
        a[0] = 1;
        for(int i = 1; i <= m; ++i) {
            cin >> a[i];
        }
        a[m + 1] = n;
        sort(a, a + m + 2);
        int v = n;
        for(int i = 2; i < m + 1; ++i) {
            if(a[i] - a[i - 1] - 1 > 0) {
                dis.push_back(a[i] - a[i - 1] - 1);
                v = min(v, a[i] - a[i - 1] - 1);
            }
        }
        if(m >= 1 && a[1] - a[0] > 0) {
            dis.push_back(a[1] - a[0]);
            v = min(v, a[1] - a[0]);
        }
        if(m >= 1 && n - a[m] > 0) {
            dis.push_back(n - a[m]);
            v = min(v, n - a[m]);
        }
        int ans = 0;
        if(m == 0) ans = 1;
        if(dis.size()) {
            for(auto d : dis) {
                ans += d / v;
                if(d % v) ans++;
            }
        }
        cout << ans << endl;
        return 0;
    }
    
    E - Sequence Matching

    Solution

    直接套最小编辑距离的板子

    #include <iostream>
    #include <algorithm>
    using namespace std;
    
    const int INF = 0x3f3f3f3f;
    
    int dp[1005][1005];     /*dp[i][j]表示表示A串从第0个字符开始到第i个字符和B串从第0个字符开始到第j个字符,这两个字串的编辑距离。字符串的下标从1开始。*/
    int a[1005],b[1005];   //a,b字符串从下标1开始
    int n, m;
    
    int EditDis()
    {
        int len1 = n;
        int len2 = m;
        //初始化
        for(int i=1;i<=len1;i++)
            for(int j=1;j<=len2;j++)
                dp[i][j] = INF;
        for(int i=1;i<=len1;i++)
            dp[i][0] = i;
        for(int j=1;j<=len2;j++)
            dp[0][j] = j;
        for(int i=1;i<=len1;i++)
        {
            for(int j=1;j<=len2;j++)
            {
                int flag;
                if(a[i]==b[j])
                    flag=0;
                else
                    flag=1;
                dp[i][j]=min(dp[i-1][j]+1,min(dp[i][j-1]+1,dp[i-1][j-1]+flag));
                //dp[i-1][j]+1表示删掉字符串a最后一个字符a[i]
                //dp[i][j-1]+1表示给字符串添加b最后一个字符
                //dp[i-1][j-1]+flag表示改变,相同则不需操作次数,不同则需要,用flag记录
            }
        }
        return dp[len1][len2];
    }
    
    int main()
    {
        cin >> n >> m;
        for(int i = 1; i <= n; ++i) cin >> a[i];
        for(int j = 1; j <= m; ++j) cin >> b[j];
        cout << EditDis() << endl;
        return 0;
    }
    
    F - Range Xor Query

    Solution

    线段树裸题,由于处理的是异或运算,所以树状数组同样可以求解,亲测效率更高。

    线段树版本:

    #include <iostream>
    #include <cstring>
    #include <algorithm>
    using namespace std;
    
    typedef long long ll;
    
    const int maxn = 1111111;
    
    ll tree[maxn], n, q, arr[maxn];
    
    void build(int ad, int l, int r)
    {
        if(l == r) {
            tree[ad] = arr[l];
            return;
        }
        int mid = (l + r) >> 1;
        build(ad << 1, l, mid);
        build(ad << 1 | 1, mid + 1, r);
        tree[ad] = tree[ad << 1] ^ tree[ad << 1 | 1];
        return;
    }
    
    void change(int ad, int l, int r, int d, ll ch)
    {
        if(l == r) {
            if(l == d) {
                tree[ad] = tree[ad] ^ ch;
            }
            return;
        }
        int mid = (l + r) >> 1;
        if(mid >= d) {
            change(ad << 1, l, mid, d, ch);
        }
        else {
            change(ad << 1 | 1, mid + 1, r, d, ch);
        }
        tree[ad] = tree[ad << 1] ^ tree[ad << 1 | 1];
        return;
    }
    
    ll query(int ad, int l, int r, int ql, int qr)
    {
        if(r < ql || l > qr) return 0;
        if(l >= ql && r <= qr) return tree[ad];
        int mid = (l + r) >> 1;
        ll ans = 0;
        if(mid >= ql) {
            ans = ans ^ query(ad << 1, l, mid, ql, qr);
        }
        if(mid < qr) {
            ans = ans ^ query(ad << 1 | 1, mid + 1, r, ql, qr);
        }
        return ans;
    }
    
    int main()
    {
        ios_base::sync_with_stdio(false);
        cin.tie(0); cout.tie(0);
        cin >> n >> q;
        for(int i = 1; i <= n; ++i) cin >> arr[i];
        build(1, 1, n);
        while(q--) {
            ll t, x, y;
            cin >> t >> x >> y;
            if(t == 1) {
                change(1, 1, n, x, y);
            }
            else {
                cout << query(1, 1, n, x, y) << endl;
            }
        }
        return 0;
    }
    

    树状数组版本:

    #include <iostream>
    #include <algorithm>
    using namespace std;
    
    inline int lowbit(int x) { return (x & (-x)); }
    
    typedef long long ll;
    
    const int maxn = 1111111;
    
    ll tree[maxn], arr[maxn], n, q;
    
    void update(int ad, ll x) {
        while(ad <= n) {
            tree[ad] = tree[ad] ^ x;
            ad += lowbit(ad);
        }
        return;
    }
    
    ll query(int ad) {
        ll ans = 0;
        while(ad) {
            ans ^= tree[ad];
            ad -= lowbit(ad);
        }
        return ans;
    }
    
    int main()
    {
        ios_base::sync_with_stdio(false);
        cin.tie(0); cout.tie(0);
        cin >> n >> q;
        for(int i = 1; i <= n; ++i) {
            cin >> arr[i];
            update(i, arr[i]);
        }
        while(q--) {
            ll t, x, y;
            cin >> t >> x >> y;
            if(t == 1) {
                update(x, y);
            }
            else {
                cout << (query(y) ^ query(x - 1)) << endl;
            }
        }
        return 0;
    }
    

    对于两种方式都可以的题,更喜欢用树状数组写,毕竟码量少,不容易出错==。

  • 相关阅读:
    Elasticsearch--预匹配器
    Elasticsearch--建议器
    Elasticsearch--聚合
    Elasticsearch--扩展索引结构
    Elasticsearch--更好的搜索_加权得分,脚本,同义词
    Elasticsearch--搜索
    信息论基础概念
    一个人的思想决定一个人的行为,一个人的行为决定一个人的习惯,一个人的习惯决定一个人的性格,一个人的性格决定一个人的命运,一个人的命运决定一个人的一生。
    宝塔的外网地址忘记 解决办法
    一定要先看文档 hyperf
  • 原文地址:https://www.cnblogs.com/LeafLove/p/14132295.html
Copyright © 2011-2022 走看看