首页 > 其他分享 >ABC382 C-F题解

ABC382 C-F题解

时间:2024-12-07 19:43:44浏览次数:10  
标签:val rs int 题解 tag ls ABC382 NodePtr

C - Kaiten Sushi

把寿司都放到一个堆里,从前往后扫 \(A\) 数组,如果当前食客 \(A_i\) 小于等于堆顶,就取出堆顶,记录这份寿司被第 \(i\) 个人吃掉。复杂度 \(O(n\log m)\)。

D - Keep Distance

搜索回溯,但每一步从 \(10\) 枚举到 \(m\) 会超时,剪一下枝 for (int i = 10; res.back() + i <= m - 10 * (n - siz - 1); i++)

F - Falling Stars

把横线从下到上排序,开一棵线段树记录每个位置摞了多少层。要加入一条横线的时候,先查询对应区间 \([C_i,C_i+L_i-1]\) 的最小值(最高层数)\(r\),则该横线的层数就是 \(r-1\),区间赋值 \(r-1\) 即可。

#include <bits/stdc++.h>
using namespace std;

int main() {
    cin.tie(0)->sync_with_stdio(0);
    int H, W, n;
    cin >> H >> W >> n;
    struct Bar {
        int R, C, L, id;
        bool operator<(const Bar& o) const {
            return R > o.R;
        }
    };
    vector<Bar> bars(n);
    for (int i = 0; i < n; i++) {
        Bar& b = bars[i];
        cin >> b.R >> b.C >> b.L;
        b.id = i;
    }
    sort(bars.begin(), bars.end());
    class SegmentTree {
        struct Node;
        using NodePtr = shared_ptr<Node>;

        struct Node {
            int l, r, val, tag;
            NodePtr ls, rs;
            Node(int l, int r, int val, int tag,
                 NodePtr ls = nullptr,
                 NodePtr rs = nullptr)
                : l(l), r(r), val(val), tag(tag), ls(ls), rs(rs) {}
        };

       private:
        NodePtr root;
        void refresh(NodePtr p) {
            p->val = min(p->ls->val, p->rs->val);
        }
        void build(NodePtr& p, int l, int r) {
            p = make_shared<Node>(l, r, 0, 0);
            if (l == r) return;
            int mid = (l + r) >> 1;
            build(p->ls, l, mid);
            build(p->rs, mid + 1, r);
        }
        void applyFillTag(NodePtr p, int v) {
            p->val = p->tag = v;
        }
        void pushDown(NodePtr p) {
            if (!p->tag) return;
            applyFillTag(p->ls, p->tag);
            applyFillTag(p->rs, p->tag);
            p->tag = 0;
        }
        void fillRange(NodePtr p, int l, int r, int val) {
            if (l <= p->l && p->r <= r)
                return applyFillTag(p, val), void(0);
            pushDown(p);
            int mid = (p->l + p->r) >> 1;
            if (l <= mid) fillRange(p->ls, l, r, val);
            if (r > mid) fillRange(p->rs, l, r, val);
            refresh(p);
        }
        int queryMin(NodePtr p, int l, int r) {
            if (l <= p->l && p->r <= r)
                return p->val;
            pushDown(p);
            int mid = (p->l + p->r) >> 1;
            int res = INT_MAX;
            if (l <= mid) res = min(res, queryMin(p->ls, l, r));
            if (r > mid) res = min(res, queryMin(p->rs, l, r));
            return res;
        }

       public:
        SegmentTree(int l, int r) { build(root, l, r); }
        void fillRange(int l, int r, int val) { fillRange(root, l, r, val); }
        int queryMin(int l, int r) { return queryMin(root, l, r); }
    };
    SegmentTree tr(1, W);
    tr.fillRange(1, W, H + 1);
    vector<int> ans(n);
    for (auto& b : bars) {
        ans[b.id] = tr.queryMin(b.C, b.C + b.L - 1) - 1;
        tr.fillRange(b.C, b.C + b.L - 1, ans[b.id]);
    }
    for (int i = 0; i < n; i++) {
        cout << ans[i] << '\n';
    }
    return 0;
}

标签:val,rs,int,题解,tag,ls,ABC382,NodePtr
From: https://www.cnblogs.com/th19/p/18592579

相关文章

  • 【题解】洛谷P6225: [eJOI2019] 异或橙子
    P6225[eJOI2019]异或橙子结论题,要手玩几组样例就懂了,发现长度为偶数的最后削为0,否则的话下标为奇数答案就是区间下标为奇数的异或和,偶数相同,所以考虑用两个树状数组分别维护下标奇偶数的异或前缀和,然后再异或区间。#include<bits/stdc++.h>//#defineintlonglong#define......
  • CF2045H - Missing Separators 题解
    CF2045H-MissingSeparators题面您有一本字典,它是按字母顺序排列的多个单词的列表。每个单词都由大写英文字母组成。您想打印这本字典。然而,打印系统出现了一个错误,列表中的所有单词都紧挨着打印,单词之间没有任何分隔符。现在,您最终得到的字符串\(S\)是字典中所有单词按照......
  • 蓝桥杯 2024 省赛 C++ B组 R 格式 (JAVA面向对象 高精度 纯api题解)
    解题思路:由于数位较大这里采用高精度,又因为高精度写起来比较麻烦所以这里直接采用JAVAapi中的高精度浮点数类型和高精度整数类型,应为高精度浮点数类型四舍五入较为麻烦所以这里改为手动四舍五入importjava.math.BigDecimal;importjava.math.BigInteger;importjava.util......
  • 接龙数列(第十四届蓝桥杯C++B组JAVA题解 动态规划)
    对于一个长度为 KK 的整数数列:A1,A2,...,AK,我们称之为接龙数列当且仅当 Ai 的首位数字恰好等于 Ai−1 的末位数字(2≤i≤K)。例如 12,23,35,56,61,11是接龙数列;12,23,34,56不是接龙数列,因为 56的首位数字不等于 3434 的末位数字。所有长度为 11 的整数数列都......
  • 题解:AtCoder Beginner Contest AT_abc380_d ABC380D Strange Mirroring
    题目大意给定一个字符串$S$,执行$10^{100}$次以下操作:首先,令字符串$T$为字符串$S$中所有大写字母变为小写字母,小写字母变为大写字母的结果。其次,将$T$拼接在$S$后面。接下来,有一些询问:请输出在所有操作执行完成之后$S$的第$K$个字母。思路乍一看,好大的数......
  • 题解:AtCoder Beginner Contest AT_abc373_d ABC373D Hidden Weights
    题目传送门题目翻译给你一个$N$个点,$M$条边的有向图,其中边有边权。现在让你给每一个点设置一个点权$a$,使得对于任意两点$x$和$y$,如果$x$到$y$有一条边,边权为$w$,那么需要满足$a_y-a_x=w$。现在让你输出一组合法的分配方案,题目保证存在,输出任意一组都行。思路1(注意......
  • 题解:[USACO07DEC] Sightseeing Cows G
    洛谷P2868题目大意有个$n$个点,$m$条边的有向图,点有点权,边有边权。现在要找出一个环,使得点权和与边权和的比值最大。思路既然说要使得点权和与边权和的比值最大,那么就会想到$01$分数规划。二分答案就不用说了,重点是这个$check$函数。$01$分数规划的板子中要检查的是......
  • 题解:AT_abc371_c [ABC371C] Make Isomorphic
    题目大意有两个简单无向图,你每一次可以给第二个图添上或去掉一条边,有相应花费,问将两个图变为同构最少需要花费多少钱。思路观察数据范围,可以发现$N$非常小,可以考虑枚举全排列。所以我们就暴力枚举$1$到$N$,把这个当前排列记在一个数组里,$t[i]$表示在第一个图中点$i$对应......
  • 题解:AT_abc366_d [ABC366D] Cuboid Sum Query
    这是一个区间求和问题,因为Q很大,所以使用前缀和。N不超过100,所以在Q次询问中嵌套一次O(n)的循环是不会超时的。令s[i][j][k]表示第i层中左上角为(1,1),右下角为(j,k)的矩形中所有元素的和。s[i][j][k]=s[i][j-1][k]+s[i][j][k-1]-s[i][j-1][k-1]+a[i][j][k];然后在Q次询问中,枚举层数......
  • 题解:AT_abc369_e [ABC369E] Sightseeing Tour
    题目大意给定一个$N$个点,$M$条边的无向图。其中边有边权。有$Q$次询问,每一次给你$K$条必须经过的边(但是方向没有限制),问从$1$到$N$的最短路长度是多少。思路观察数据范围,可以发现:虽然$M$很大,但是$N$和$K$并不大。$K\le5$,可以暴力枚举每一条边经过时的方向以及......