社区讨论

95pts WA#7 求助

P3227[HNOI2013] 切糕参与者 7已保存回复 6

讨论操作

快速查看讨论及其快照的属性,并进行相关操作。

当前回复
6 条
当前快照
1 份
快照标识符
@mhjifdv9
此快照首次捕获于
2025/11/04 03:05
4 个月前
此快照最后确认于
2025/11/04 03:05
4 个月前
查看原帖
CPP
// #define WANT_LDEBUG
#ifdef LOCAL
#include "D:/C++/include/all.h"
#else
#include <bits/stdc++.h>
#define ldebug(...)
#define cpp_version_ __cplusplus
#define REP(i, a, b) for (int i = a; i < (b); ++i)
#define RREP(i, a, b) for (int i = a; i > (b); --i)
#define FOR(i, a, b) for (int i = a; i <= (b); ++i)
#define RFOR(i, a, b) for (int i = a; i >= (b); --i)
#define REPK(i, a, b, k) for (int i = a; i < (b); i += k)
#define RREPK(i, a, b, k) for (int i = a; i > (b); i -= k)
#define FORK(i, a, b, k) for (int i = a; i <= (b); i += k)
#define RFORK(i, a, b, k) for (int i = a; i >= (b); i -= k)
using namespace std;
using bool_t = signed char;
using u32 = unsigned int;
using i64 = long long;
using i128 = __int128;
using u64 = unsigned long long;
using f64 = double;
#define fast_io()                                                              \
    std::ios::sync_with_stdio(false);                                          \
    std::cin.tie(nullptr)
template <typename T, typename U> bool ckmax(T &a, U b) {
    return a < b && (a = b, true);
}
template <typename T, typename U> bool ckmin(T &a, U b) {
    return b < a && (a = b, true);
}
#endif

/* code-snippet max_flow */
#include <utility>
#include <functional>
#include <limits>
#include <queue>
#include <type_traits>
#include <vector>

class max_flow {
private:
    using u32 = unsigned int;

    struct edge {
        u32 v, p, f;
        edge() = default;
        edge(u32 v_, u32 p_, u32 f_) : v(v_), p(p_), f(f_) {}
    };
    u32 source, sink, v_cnt, e_cnt;
    bool set_s, set_t;
    std::vector<u32> h, now, dep;
    std::vector<edge> e;
    std::queue<u32> q;

    bool bfs() {
        now = h;
        dep.assign(v_cnt, 0);
        dep[source] = 1;
        q.push(source);
        while (!q.empty()) {
            u32 u = q.front();
            q.pop();
            for (u32 go = h[u]; ~go; go = e[go].p) {
                if (!e[go].f) {
                    continue;
                }
                u32 v = e[go].v;
                if (!dep[v]) {
                    dep[v] = dep[u] + 1;
                    q.push(v);
                }
            }
        }
        return dep[sink] > 0;
    }
    u32 dfs(u32 u, u32 flow) {
        if (u == sink) {
            return flow;
        }
        u32 res = 0;
        for (u32 go = now[u]; ~go && flow; go = e[go].p) {
            u32 v = e[go].v, f = e[go].f;
            now[u] = go;
            if (!f || dep[u] + 1 != dep[v]) {
                continue;
            }
            u32 k = dfs(v, std::min(flow, f));
            if (!k) {
                dep[v] = 0;
            } else {
                e[go].f -= k;
                e[go ^ 1].f += k;
                res += k;
                flow -= k;
            }
        }
        return res;
    }
public:
    max_flow() : v_cnt{}, e_cnt{} {}
    //! new_node
    u32 operator!() {
        u32 u = v_cnt++;
        h.push_back(~0U);
        return u;
    }
    //! add_edge
    void operator()(u32 u, u32 v, u32 f) {
        ldebug("{} {} {}\n", u, v, f);
#ifdef DEBUG
        if (u >= v_cnt || v >= v_cnt) {
            throw(range_error("invalid vertex"));
        }
#endif
        e.emplace_back(v, h[u], f);
        h[u] = e_cnt++;
        e.emplace_back(u, h[v], 0);
        h[v] = e_cnt++;
    }
    //! default source and sink
    void operator~() {
        source = operator!();
        sink = operator!();
        set_s = set_t = true;
    }
    //! set source
    void operator+=(u32 s) {
        source = s;
        set_s = true;
    }
    //! set sink
    void operator-=(u32 t) {
        sink = t;
        set_t = true;
    }
    //! get source
    u32 operator+() {
#ifdef DEBUG
        if (!set_s) {
            throw(runtime_error("source haven't set"));
        }
#endif
        return source;
    }
    //! get sink
    u32 operator-() {
#ifdef DEBUG
        if (!set_t) {
            throw(runtime_error("sink haven't set"));
        }
#endif
        return sink;
    }
    //! max_flow
    u32 operator*() {
#ifdef DEBUG
        if (!set_s || !set_t) {
            throw(runtime_error("source & sink aren't set"));
        }
        if (source >= v_cnt || sink >= v_cnt) {
            throw(runtime_error("bad source & sink id"));
        }
#endif
        u32 flow = 0;
        while (bfs()) {
            flow += dfs(source, std::numeric_limits<u32>::max());
        }
        return flow;
    }
};
/* code-snippet max_flow */

constexpr u32 INF = 2e9;
constexpr int dx[4] = {-1, 0, 1, 0}, dy[4] = {0, -1, 0, 1};
int P, Q, R, D;
vector<vector<vector<int>>> a;
vector<vector<vector<u32>>> id;
max_flow mf;

struct edge {
    int p, v, f, c;
    edge() {}
    edge(int a, int b, int d, int e) : p(a), v(b), f(d), c(e) {}
};

void solve() {
    cin >> P >> Q >> R >> D;
    a.assign(R, vector<vector<int>>(P, vector<int>(Q)));
    id.assign(R + 1, vector<vector<u32>>(P, vector<u32>(Q)));
    ~mf;
    REP(i, 0, R) {
        REP(j, 0, P) {
            REP(k, 0, Q) {
                cin >> a[i][j][k];
                id[i][j][k] = !mf;
            }
        }
    }
    REP(i, 0, P) {
        REP(j, 0, Q) {
            id[R][i][j] = !mf;
            mf(+mf, id[0][i][j], INF);
            mf(id[R][i][j], -mf, INF);
        }
    }
    REP(i, 0, P) {
        REP(j, 0, Q) {
            REP(k, 0, R) {
                mf(id[k][i][j], id[k + 1][i][j], a[k][i][j]);
                mf(id[k + 1][i][j], id[k][i][j], INF);
            }
            REP(l, 0, 4) {
                int nx = i + dx[l], ny = j + dy[l];
                if (nx < 0 || nx >= P || ny < 0 || ny >= P) {
                    continue;
                }
                FOR(k, D, R) {
                    // ldebug("{} {} {}\n", k, i, j);
                    mf(id[k][i][j], id[k - D][nx][ny], INF);
                    // mf(id[k - D][nx][ny], id[k][i][j], INF);
                }
            }
        }
    }
    cout << *mf << '\n';
}
int main() {
    fast_io();
    int T = 1;
    // cin >> T;
    while (T--) {
        solve();
#ifdef DEBUG
        cerr << endl;
#endif
    }
    return 0;
}

回复

6 条回复,欢迎继续交流。

正在加载回复...