zoukankan      html  css  js  c++  java
  • 《2021CCPC桂林》

    只做了几个题。

    B. A Plus B Problem:

    一开始做的时候思路有点乱,后面理清楚了,就是说不用10进制来维护,用没有进位之后的数来维护,这样每次操作之后就是加1减1的操作了。

    // Author: levil
    #include<bits/stdc++.h>
    using namespace std;
    typedef long long LL;
    typedef long double ld;
    typedef pair<int,int> pii;
    const int N = 2e6 + 5;
    const int M = 1e6 + 5;
    const LL Mod = 998244353;
    #define INF 1e9
    #define dbg(ax) cout << "now this num is " << ax << endl;
    inline long long ADD(long long x,long long y) {
        if(x + y < 0) return ((x + y) % Mod + Mod) % Mod;
        return (x + y) % Mod;
    }
    inline long long MUL(long long x,long long y) {
        if(x * y < 0) return ((x * y) % Mod + Mod) % Mod;
        return x * y % Mod;
    }
    inline long long DEC(long long x,long long y) {
        if(x - y < 0) return (x - y + Mod) % Mod;
        return (x - y) % Mod;
    }
    
    int a[5][N],cd[N];
    struct Node{int L,r,mi,mx,tag;}node[N << 2];
    void Pushup(int idx) {
        node[idx].mx = max(node[idx << 1].mx,node[idx << 1 | 1].mx);
        node[idx].mi = min(node[idx << 1].mi,node[idx << 1 | 1].mi);
    }
    void Pushdown(int idx) {
        if(node[idx].tag != 0) {
            int tag = node[idx].tag;
            node[idx << 1].mx += tag,node[idx << 1].mi += tag,node[idx << 1].tag += tag;
            node[idx << 1 | 1].mx += tag,node[idx << 1 | 1].mi += tag,node[idx << 1 | 1].tag += tag;
            node[idx].tag = 0;
        }
    }
    void build(int L,int r,int idx) {
        node[idx].L = L,node[idx].r = r,node[idx].tag = 0;
        if(L == r) {
            node[idx].mi = node[idx].mx = cd[L];
            return ;
        }
        int mid = (L + r) >> 1;
        build(L,mid,idx << 1);
        build(mid + 1,r,idx << 1 | 1);
        Pushup(idx);
    }
    void update(int L,int r,int val,int idx) {
        if(node[idx].L > node[idx].r || L > r) return ;
        if(node[idx].L >= L && node[idx].r <= r) {
            node[idx].mi += val;
            node[idx].mx += val;
            node[idx].tag += val;
            return ;
        }
        Pushdown(idx);
        int mid = (node[idx].L + node[idx].r) >> 1;
        if(mid >= L) update(L,r,val,idx << 1);
        if(mid < r) update(L,r,val,idx << 1 | 1);
        Pushup(idx);
    }
    void update2(int x,int val,int idx) {
        if(node[idx].L == node[idx].r) {
            node[idx].mi = node[idx].mx = val;
            return ;
        }
        Pushdown(idx);
        int mid = (node[idx].L + node[idx].r) >> 1;
        if(mid >= x) update2(x,val,idx << 1);
        else update2(x,val,idx << 1 | 1);
        Pushup(idx);
    }
    int query(int x,int idx) {
        if(node[idx].L == node[idx].r) return node[idx].mi;
        Pushdown(idx);
        int mid = (node[idx].L + node[idx].r) >> 1;
        if(mid >= x) return query(x,idx << 1);
        else return query(x,idx << 1 | 1);
    }
    int query_pos(int L,int r,int id,int idx) {//id = 1 != 10,id = 2,!= 9
        if(L > r) return -1;
        if(node[idx].L == node[idx].r) return node[idx].L;
        Pushdown(idx);
        int mid = (node[idx].L + node[idx].r) >> 1,val = 9;
        if(id == 1) val = 10;
        if(mid < r && (node[idx << 1 | 1].mx != val || node[idx << 1 | 1].mi != val)) {
            int ans = query_pos(L,r,id,idx << 1 | 1);
            if(ans != -1) return ans;
            else if(mid >= L && (node[idx << 1].mx != val || node[idx << 1].mi != val)) return query_pos(L,r,id,idx << 1);
            return -1; 
        }
        else if(mid >= L && (node[idx << 1].mx != val || node[idx << 1].mi != val)) return query_pos(L,r,id,idx << 1);
        return -1;
    }
    void solve() {
        int n,q;scanf("%d %d",&n,&q);
        string s;cin >> s;
        for(int i = 1;i <= n;++i) a[1][i] = s[i - 1] - '0';
        cin >> s;
        for(int i = 1;i <= n;++i) a[2][i] = s[i - 1] - '0';
        int t = 0;
        for(int i = n;i >= 1;--i) {
            int f = (a[1][i] + a[2][i] + t) / 10;
            cd[i] = a[1][i] + a[2][i] + t;
            t = f;
        }
        build(1,n,1);
        while(q--) {
            int r,c,d;scanf("%d %d %d",&r,&c,&d);
            int ch = 0,id;
            if(r == 1) id = 1;
            else id = 2;
            if(a[id][c] != d) ch++;
            int dis = a[id][c] - d;
            a[id][c] = d;
            int tmp = query(c,1);
            int ed = tmp - dis;
            if(tmp != ed) ch++;
            update2(c,ed,1);
            if(ed < 10 && tmp >= 10){
                int pos = query_pos(1,c - 1,1,1);
                if(pos == -1) pos = 1,ch += c - 1;
                else ch += c - pos;
                update(pos,c - 1,-1,1);
            }
            else if(ed >= 10 && tmp < 10) {
                int pos = query_pos(1,c - 1,2,1);
                if(pos == -1) pos = 1,ch += c - 1;
                else ch += c - pos;
                update(pos,c - 1,1,1);
            }
            printf("%d %d\n",ed % 10,ch);
        }
    
    
    }   
    int main() {
      //  int ca;scanf("%d",&ca);
       // while(ca--) {
            solve();
        //}
        //system("pause");
        return 0;
    }
    /*
    5 5
    05617
    14382
    1 3 2
    2 5 4
    
    5 5
    26321
    47764
    2 5 9
    2 4 7
    1 4 2
    1 3 2
    1 4 3
    
    5 5
    99990
    00000
    2 4 1
    2 5 1
    2 5 1
    */
    View Code

    E:Buy and Delete

    这题相对要简单一些,只要能想到了,主要是判断能不能买到环的情况,如果能买到一个,和买到多个一样都是2轮。也就是说找到一个环的权值最小。

    dij找一下最小权值环就行了。

    D:Assumption is All You Need 银牌题?

    这感觉也就是个2000多分左右的构造,不是很难,大概半小时推出了解法。

    考虑对于一个小的数,一次逆序对操作之后,它只会向前走。

    我们拟定现在比它小的数都无法动了。那么如果目标位置在它后面,那么如果不靠比它小的肯定无解。

    现在我们去动比它小的,很显然,这个移动规律有传递性,如果我们利用比它小的完成了,那么比它小的肯定在更前面了。

    所以我们考虑从小到大去对位,那么对于当前i,如果需要借用小的,那么肯定无解。

    经过上面操作很显然,我们每次去动都是向左移动,那么每次对位我们都去找一个可动区间里的最小的替换它是最优的。

    最优的这个很容易证明,因为比他大的都可以移动到这个位置,所以找最小的。

    // Author: levil
    #include<bits/stdc++.h>
    using namespace std;
    typedef long long LL;
    typedef long double ld;
    typedef pair<int,int> pii;
    const int N = 2e6 + 5;
    const int M = 1e6 + 5;
    const LL Mod = 998244353;
    #define INF 1e9
    #define dbg(ax) cout << "now this num is " << ax << endl;
    inline long long ADD(long long x,long long y) {
        if(x + y < 0) return ((x + y) % Mod + Mod) % Mod;
        return (x + y) % Mod;
    }
    inline long long MUL(long long x,long long y) {
        if(x * y < 0) return ((x * y) % Mod + Mod) % Mod;
        return x * y % Mod;
    }
    inline long long DEC(long long x,long long y) {
        if(x - y < 0) return (x - y + Mod) % Mod;
        return (x - y) % Mod;
    }
    
    int a[2025],b[2025],pos1[2025],pos2[2025];
    vector<pii> ans;
    int Find(int L,int r,int k) {
        int mi = INF;
        for(int i = L;i <= r;++i) {
            if(a[i] > k && a[i] < mi) mi = a[i];
        }
        return mi;
    } 
    void change(int x,int y) {
        int xx = pos1[x],yy = pos1[y];
        pos1[y] = xx,pos1[x] = yy;
        swap(a[xx],a[yy]);
        ans.push_back(pii{min(xx,yy),max(xx,yy)});
    }
    void solve() {
        ans.clear();
        int n;scanf("%d",&n);
        for(int i = 1;i <= n;++i) scanf("%d",&a[i]),pos1[a[i]] = i;
        for(int i = 1;i <= n;++i) scanf("%d",&b[i]),pos2[b[i]] = i;
        bool flag = 0;
        for(int i = 1;i <= n;++i) {
            if(pos2[i] > pos1[i]) {flag = 1;break;}
            while(1) {
                int tmp = Find(pos2[i],pos1[i] - 1,i);
                if(tmp == INF) break;
                change(i,tmp);
            }
            if(pos1[i] != pos2[i]) change(i,a[pos2[i]]);
        }
        if(flag) printf("-1\n");
        else {  
            printf("%d\n",ans.size());
            for(auto v : ans) printf("%d %d\n",v.first,v.second);
        }
    
    }   
    int main() {
        int ca;scanf("%d",&ca);
        while(ca--) {
            solve();
        }
        //system("pause");
        return 0;
    }
    View Code
  • 相关阅读:
    c语言练习17——输入一行字符,分别统计出其中英文字母、空格、数字和其它字符的个数
    c语言练习16——输入两个正整数m和n,求其最大公约数和最小公倍数
    c语言练习15——条件运算符的嵌套
    c语言练习14——将一个正整数分解质因数
    CentOS下Cassandra集群搭建
    一台linux服务器挂载另外一台linux服务器文件系统
    zabbix分布式监控多网段的部署与实现
    CentOS安装MySQL详解
    vcenter 7.0 安装 vRealize Operations Manager
    Zabbix分布式部署详细
  • 原文地址:https://www.cnblogs.com/zwjzwj/p/15571983.html
Copyright © 2011-2022 走看看