zoukankan      html  css  js  c++  java
  • 省选测试15

    啥也不会,就没交

    A U.N.OWEN就是她吗?

    题目大意 : n堆石子,每次选一个区间扔 (k_i) 个,不够就全扔,让扔出去的石子序列字典序最大

    • 把所有没有被任何区间覆盖的点扔掉,得到新的a序列

    • 把所有的区间按左端点排序,定义 (b_i) 为排序后第 i 个区间拿的石子数

    • 令A为a的前缀和,B为b的前缀和,我们需要时刻满足 (forall i<j,B_j-B_{i-1}leq A_{r_j}-A_{l_i-1})

    • (C_j=B_j-A_{r_j},D_i=B_{i-1}-A_{l_i-1}),就是 (forall i<j,C_jleq D_i)

    • 对于 (jin [t,m]), (C_j) 会加上 k,对于 (iin [t+1,m]), (D_i) 会加上 k

    • 那么,只有对于 (iin [1,t],jin [t,m]) 的限制会有变化

    • 也就是说 (iin [1,t],jin [t,m],C_j+kleq D_i)(iin [1,t],jin [t,m],kleq D_i-C_j) ,D取最小值C取最大值即可得到最大的k

    • 那么用线段树维护C和D的变化即可

    Code

    Show Code
    #include <cstdio>
    #include <algorithm>
    #define ls (rt << 1)
    #define rs (rt << 1 | 1)
    
    using namespace std;
    const int N = 3e5 + 5;
    
    int read(int x = 0, int f = 1, char c = getchar()) {
        for (; c < '0' || c > '9'; c = getchar())
            if (c == '-') f = -1;
        for (; c >='0' && c <='9'; c = getchar())
            x = x * 10 + c - '0';
        return x * f;
    }
    
    int n, m, s[N], b[N], sa[N], rk[N];
    int t1[N*4], tag1[N*4], t2[N*4], tag2[N*4];
    
    struct Ques {
        int l, r, k;
    }q[N];
    
    bool Cmp(const int &x, const int &y) {
        return q[x].l < q[y].l;
    }
    
    void Build1(int rt, int l, int r) {
        if (l == r) return t1[rt] = -s[q[sa[l]].l-1], void();
        int mid = l + r >> 1;
        Build1(ls, l, mid); Build1(rs, mid+1, r);
        t1[rt] = min(t1[ls], t1[rs]);
    }
    
    void Pushdown1(int rt) {
        int x = tag1[rt]; tag1[rt] = 0;
        t1[ls] += x; tag1[ls] += x; t1[rs] += x; tag1[rs] += x;
    }
    
    void Add1(int rt, int l, int r, int x, int w) {
        if (x <= l) return t1[rt] += w, tag1[rt] += w, void();
        if (tag1[rt]) Pushdown1(rt);
        int mid = l + r >> 1;
        if (x <= mid) Add1(ls, l, mid, x, w);
        Add1(rs, mid + 1, r, x, w);
        t1[rt] = min(t1[ls], t1[rs]);
    }
    
    int Ask1(int rt, int l, int r, int x, int y) {//min
        if (x <= l && r <= y) return t1[rt];
        if (tag1[rt]) Pushdown1(rt);
        int mid = l + r >> 1, ans = 2e9;
        if (x <= mid) ans = Ask1(ls, l, mid, x, y);
        if (y > mid) ans = min(ans, Ask1(rs, mid+1, r, x, y));
        return ans;
    }
    
    void Build2(int rt, int l, int r) {
        if (l == r) return t2[rt] = -s[q[sa[l]].r], void();
        int mid = l + r >> 1;
        Build2(ls, l, mid); Build2(rs, mid+1, r);
        t2[rt] = max(t2[ls], t2[rs]);
    }
    
    void Pushdown2(int rt) {
        int x = tag2[rt]; tag2[rt] = 0;
        t2[ls] += x; tag2[ls] += x; t2[rs] += x; tag2[rs] += x;
    }
    
    void Add2(int rt, int l, int r, int x, int w) {
        if (x <= l) return t2[rt] += w, tag2[rt] += w, void();
        if (tag2[rt]) Pushdown2(rt);
        int mid = l + r >> 1;
        if (x <= mid) Add2(ls, l, mid, x, w);
        Add2(rs, mid + 1, r, x, w);
        t2[rt] = max(t2[ls], t2[rs]);
    }
    
    int Ask2(int rt, int l, int r, int x, int y) {//min
        if (x <= l && r <= y) return t2[rt];
        if (tag2[rt]) Pushdown2(rt);
        int mid = l + r >> 1, ans = -2e9;
        if (x <= mid) ans = Ask2(ls, l, mid, x, y);
        if (y > mid) ans = max(ans, Ask2(rs, mid+1, r, x, y));
        return ans;
    }
    
    int main() {
        n = read();
        for (int i = 1; i <= n; ++i) s[i] = read();
        m = read();
        for (int i = 1; i <= m; ++i) {
            int l = read(), r = read();
            q[i] = (Ques) {l, r, read()};
            b[l]++, b[r+1]--; sa[i] = i;
        }
        sort(sa + 1, sa + m + 1, Cmp);
        for (int i = 1; i <= m; ++i)
            rk[sa[i]] = i;
        for (int i = 1, sum = 0; i <= n; ++i)
            s[i] = s[i-1] + ((sum += b[i]) ? s[i] : 0);
        Build1(1, 1, m); Build2(1, 1, m);
        for (int i = 1; i <= m; ++i) {
            int x = rk[i], k = min(q[i].k, Ask1(1, 1, m, 1, x) - Ask2(1, 1, m, x, m));
            Add1(1, 1, m, x + 1, k); Add2(1, 1, m, x, k);
            printf("%d
    ", k);
        }
        return 0;
    }
    

    B 哈德曼的妖怪少女 (Unaccepted)

    题目大意 :

    • 咕咕

    Code

    Show Code

    C 平安时代的外星人 (Unaccepted)

    题目大意 :

    • 咕咕

    Code

    Show Code
  • 相关阅读:
    centos出现“FirewallD is not running”怎么办
    Centos7开放及查看端口
    phpRedis函数使用总结
    如何在Windows的PHPstudy中使用redis
    Redis命令操作详解
    不可不知 DDoS的攻击原理与防御方法
    DDoS 攻击与防御:从原理到实践
    ORM Integrity constraint violation: 1052 Column 'id' in where clause is ambiguous
    PHP常用函数大全500+
    Linux彻底卸载Nginx
  • 原文地址:https://www.cnblogs.com/shawk/p/14413101.html
Copyright © 2011-2022 走看看