zoukankan      html  css  js  c++  java
  • ARC085F NRE

    看了题解。

    题目大意

    你有一个长度为 (N) 的全为 (0) 的序列 (A),给你一个长度同样为 (N)(0/1) 序列 (B),允许你对把 (A) 的一些区间中的数组全部改成 (1),最小化 (A)(B) 数字不同的位置个数。

    解法

    https://img.atcoder.jp/arc085/editorial.pdf

    题解写得很清楚了。。。

    总之就是把要求的东西进行一些奇妙变换,免去了变为 (1) 的代价计算,把添加线段的那个没法优化的转移给换掉。。。

    UPD:那个转换没有必要,直接 DP 即可。。。

    实现

    #include <bits/stdc++.h>
    
    using namespace std;
    
    const int INF = 2e9;
    
    struct Node {
        typedef Node* NP;
        NP l, r;
        int sz, mi;
        Node(int _sz) : l(NULL), r(NULL), sz(_sz) {
            mi = INF;
            if (sz == 1) return;
            l = new Node(sz/2);
            r = new Node(sz-sz/2);
        }
        void set(int k, int v) {
            if (sz == 1) {
                mi = min(mi, v);
                return;
            }
            if (k < sz/2) {
                l->set(k, v);
            } else {
                r->set(k-sz/2, v);
            }
            mi = min(l->mi, r->mi);
        }
        int get(int a, int b) {
            if (b <= 0 || sz <= a) return INF;
            if (a <= 0 && sz <= b) return mi;
            return min(l->get(a, b), r->get(a-sz/2, b-sz/2));
        }
    };
    
    const int MN = 200010;
    int n, q;
    int b[MN];
    vector<int> v[MN];
    
    int main() {
        cin.tie(0);
        ios::sync_with_stdio(false);
    
        cin >> n;
        int ans = 0;
        for (int i = 0; i < n; i++) {
            cin >> b[i];
            if (b[i] == 0) {
                ans++;
                b[i]--;
            }
        }
        cin >> q;
        for (int i = 0; i < q; i++) {
            int l, r;
            cin >> l >> r; l--;
            v[l].push_back(r);
        }
        Node* tr = new Node(n+1);
        for (int i = 0; i <= n; i++) {
            if (i) {
                tr->set(i, tr->get(i-1, i) + b[i-1]);
            } else {
                tr->set(0, 0);
            }
            for (int j = 0; j < int(v[i].size()); j++) {
                int r = v[i][j];
                tr->set(r, tr->get(i, r));
            }
        }
        ans += tr->get(n, n+1);
        cout << ans << endl;
        return 0;
    }
    
  • 相关阅读:
    树的定义与存储
    软件测试概论二
    软件测试概论
    抽象数据类型
    java编程总结01---20190214
    java 按行读取本文文件并存放到mongodb中
    刷题感悟
    刷题感悟- Binary Tree Path Sum
    java io与nio
    java IO 学习笔记
  • 原文地址:https://www.cnblogs.com/hfccccccccccccc/p/10234805.html
Copyright © 2011-2022 走看看