結果

問題 No.3214 small square
ユーザー dp_ijk
提出日時 2025-07-25 22:49:21
言語 C++23
(gcc 13.3.0 + boost 1.87.0)
結果
TLE  
実行時間 -
コード長 8,710 bytes
コンパイル時間 2,258 ms
コンパイル使用メモリ 183,276 KB
実行使用メモリ 288,664 KB
最終ジャッジ日時 2025-07-25 22:49:29
合計ジャッジ時間 7,597 ms
ジャッジサーバーID
(参考情報)
judge2 / judge4
このコードへのチャレンジ
(要ログイン)
ファイルパターン 結果
sample AC * 3
other AC * 10 TLE * 1 -- * 29
権限があれば一括ダウンロードができます

ソースコード

diff #

#include <algorithm>
#include <array>
#include <bit>
#include <cassert>
#include <cmath>
#include <concepts>
#include <cstddef>
#include <cstdint>
#include <cstdlib>
#include <deque>
#include <functional>
#include <iomanip>
#include <iostream>
#include <iterator>
#include <limits>
#include <map>
#include <numeric>
#include <optional>
#include <queue>
#include <random>
#include <ranges>
#include <set>
#include <sstream>
#include <stdexcept>
#include <string>
#include <tuple>
#include <type_traits>
#include <utility>
#include <vector>
struct IOSetup {
    IOSetup() {
        std::cin.tie(nullptr);
        std::ios::sync_with_stdio(false);
        std::cout << std::fixed << std::setprecision(15);
        std::cerr << std::fixed << std::setprecision(8);
    }
};
IOSetup iosetup;
using int128_t = __int128;
using uint128_t = unsigned __int128;
template <typename T>
constexpr auto rep_iota_impl(T start, T stop) noexcept {
    return std::views::iota(start, (start < stop ? stop : start));
}
template <typename T = int64_t>
constexpr auto rep_impl(auto start, auto stop) noexcept {
    return rep_iota_impl<T>(start, stop);
}
template <typename T = int64_t>
constexpr auto rep_impl(auto stop) noexcept {
    return rep_iota_impl<T>(0, stop);
}
template <class... Ts>
inline void read(Ts&... ts) {
    (std::cin >> ... >> ts);
}
template <class T, class U>
inline bool chmax(T& a, U b) {
    if (a < b) {
        a = b;
        return true;
    }
    return false;
}
template <class T, class U>
inline bool chmin(T& a, U b) {
    if (a > b) {
        a = b;
        return true;
    }
    return false;
}
using std::vector;
template <typename X>
struct MAdd {
    using ll = int64_t;
    using T = X;
    static constexpr T op(const T& x, const T& y) noexcept { return x + y; }
    static constexpr T inverse(const T& x) noexcept { return -x; }
    static constexpr T power(const T& x, ll n) noexcept { return T{x} * n; }
    static constexpr T unit() noexcept { return T{}; }
    static constexpr bool is_unit(const T& x) noexcept { return x == T{}; }
    static constexpr bool commutative = 1;
    static constexpr bool invertible = 1;
};
template <typename T>
void put(const T& t) {
    std::cout << t;
}
template <typename... Ts>
void print(const Ts&... ts) {
    put(ts...);
    std::cout << "\n";
}
using std::cin;
using std::cout;
using std::map;
using std::pair;
using std::set;
using std::string;
using std::tuple;
using std::vector;
using ll = int64_t;
template <typename MX_, typename MA_, auto operate, auto default_factory>
struct DynamicLazySegTree {
    public:
    using ll = int64_t;
    using MX = MX_;
    using MA = MA_;
    using X = typename MX::T;
    using A = typename MA::T;
    using value_type = typename MX::T;
    static_assert(std::is_invocable_v<decltype(operate), X, A, ll>);
    struct Node;
    using Tree = Node*;
    struct Node {
        X val;
        A lazy;
        Tree left, right;
        Node()
            : val(MX::unit()),
              lazy(MA::unit()),
              left(nullptr),
              right(nullptr) {}
    };
    auto _new(ll nL, ll nR) {
        auto t = new Node();
        t->val = default_factory(nL, nR);
        return t;
    }
    inline void _del(Tree t) { delete t; }
    void _delete_subtree(Tree t) {
        if (!t) return;
        _delete_subtree(t->left);
        _delete_subtree(t->right);
        _del(t);
    }
    void clear() {
        _delete_subtree(root);
        root = nullptr;
    }
    Tree root;
    const ll maxlen;
    DynamicLazySegTree() = default;
    explicit DynamicLazySegTree(ll maxlen_)
        : root(_new(0, maxlen_)),
          maxlen(maxlen_) {
        assert(maxlen_ >= 0);
    }

    private:
    void apply_subtree(Tree t, const A& a, const ll nL, const ll nR) const {
        assert(nL < nR);
        t->val = operate(t->val, a, nR - nL);
        t->lazy = MA::op(t->lazy, a);
    }
    void push_lazy(Tree t, ll nL, ll nR) {
        assert(nR - nL >= 2);
        if (nR - nL == 1) return;
        assert(t);
        if (t->lazy == MA::unit()) return;
        ll m = std::midpoint(nL, nR);
        if (!t->left) t->left = _new(nL, m);
        if (!t->right) t->right = _new(m, nR);
        apply_subtree(t->left, t->lazy, nL, m);
        apply_subtree(t->right, t->lazy, m, nR);
        t->lazy = MA::unit();
    }
    void update(Tree t, ll nL, ll nR) {
        assert(t);
        assert(nR - nL >= 2);
        if (nR - nL == 1) return;
        ll m = std::midpoint(nL, nR);
        X vL = t->left ? t->left->val : default_factory(nL, m);
        X vR = t->right ? t->right->val : default_factory(m, nR);
        t->val = MX::op(vL, vR);
    }

    public:
    X fold(ll l, ll r) { return _fold(l, r, MA::unit(), root, 0, maxlen); }
    X fold_all() { return fold(0, maxlen); }
    X _fold(ll l, ll r, const A lazy, Tree t, const ll nL, const ll nR) {
        chmax(l, nL);
        chmin(r, nR);
        if (not(l < r)) return MX::unit();
        if (!t) { return operate(default_factory(l, r), lazy, r - l); }
        if (l == nL && r == nR) { return operate(t->val, lazy, r - l); }
        ll m = std::midpoint(nL, nR);
        A nlazy = MA::op(t->lazy, lazy);
        X vL = _fold(l, r, nlazy, t->left, nL, m);
        X vR = _fold(l, r, nlazy, t->right, m, nR);
        return MX::op(vL, vR);
    }
    void apply(const ll l, const ll r, const A& a) { _apply(l, r, a, root, 0, maxlen); }
    Tree _apply(ll l, ll r, const A a, Tree t, const ll nL, const ll nR) {
        if (a == MA::unit()) return t;
        if (!t) t = _new(nL, nR);
        chmax(l, nL);
        chmin(r, nR);
        if (not(l < r)) return t;
        if (l == nL && r == nR) {
            apply_subtree(t, a, nL, nR);
            return t;
        }
        push_lazy(t, nL, nR);
        ll m = std::midpoint(nL, nR);
        t->left = _apply(l, r, a, t->left, nL, m);
        t->right = _apply(l, r, a, t->right, m, nR);
        update(t, nL, nR);
        return t;
    }
    void set(const ll i, const X& x) {
        assert(0 <= i && i < maxlen);
        root = _set(i, x, root, 0, maxlen);
    }
    Tree _set(const ll i, const X& x, Tree t, const ll nL, const ll nR) {
        if (nR - nL == 1) {
            t->val = x;
            t->lazy = MA::unit();
            return t;
        }
        push_lazy(t, nL, nR);
        ll m = std::midpoint(nL, nR);
        if (!t->left) t->left = _new(nL, m);
        if (!t->right) t->right = _new(m, nR);
        if (i < m) {
            t->left = _set(i, x, t->left, nL, m);
        } else {
            t->right = _set(i, x, t->right, m, nR);
        }
        update(t, nL, nR);
        return t;
    }

    X operator[](ll k) const { return fold(k, k + 1); }
    X get(ll k) const { return fold(k, k + 1); }
};
constexpr int64_t INF = 23e17;
template <typename X, X INF>
struct MMax {
    using T = X;
    static constexpr T op(T x, T y) { return (x < y) ? y : x; }
    static constexpr T unit() { return -INF; }
    static constexpr bool is_unit(const T& x) { return x == -INF; }
    static constexpr bool commutative = true;
    static constexpr bool idempotent = true;
};
ll operate(ll M, ll a, [[maybe_unused]] ll sz) { return M + a; }
ll default_factory(ll l, ll r) { return 0; }
struct Point {
    ll x, y, v;
};
ll resolve(ll N, ll P, ll Q, vector<Point> XYV) {
    ll minY = INF;
    for (const auto i : rep_impl((N))) {
        auto [x, y, v] = XYV[i];
        chmin(minY, y);
    }
    for (const auto i : rep_impl((N))) {
        auto [x, y, v] = XYV[i];
        XYV[i] = {x, y - minY + (Q - 1), v};
    }
    map<ll, vector<Point>> todo;
    for (const auto i : rep_impl((N))) {
        auto [x, y, v] = XYV[i];
        todo[x].push_back({x, y, v});
    }
    set<ll> T;
    for (auto& [x, _] : todo) {
        T.insert(x - (P - 1));
        T.insert(x + 1);
    }
    auto seg = DynamicLazySegTree<MMax<ll, INF>, MAdd<ll>, operate, default_factory>(1e10);
    ll res = 0;
    for (auto t : T) {
        for (auto [x, y, v] : todo[t + (P - 1)]) {
            assert(0 <= y - (Q - 1));
            seg.apply(y - (Q - 1), y + 1, v);
        }
        for (auto [x, y, v] : todo[t - 1]) {
            assert(0 <= y - (Q - 1));
            seg.apply(y - (Q - 1), y + 1, -v);
        }
        ll nres = seg.fold_all();
        chmax(res, nres);
    }
    seg.clear();
    return res;
}
int main() {
    int64_t N, A;
    read(N, A);
    vector<Point> XYV(N);
    for (const auto i : rep_impl((N))) {
        int64_t x, y, v;
        read(x, y, v);
        XYV[i] = {x, y, v};
    }
    ll res = 0;
    for (const auto P : rep_impl((A), (A + 2)))
        for (const auto Q : rep_impl((A), (A + 2)))
            chmax(res, resolve(N, P, Q, XYV));
    print(res);
}
0