QOJ.ac
QOJ
ID | Problem | Submitter | Result | Time | Memory | Language | File size | Submit time | Judge time |
---|---|---|---|---|---|---|---|---|---|
#667478 | #7898. I Just Want... One More... | foyonaczy | WA | 4ms | 3812kb | C++20 | 3.5kb | 2024-10-22 23:24:38 | 2024-10-22 23:24:38 |
Judging History
answer
#include<bits/stdc++.h>
#define int long long
using i64 = long long;
constexpr i64 INF = 1e18;
struct Edge {
int y;
i64 w;
};
std::vector<int> v[200005];
std::vector<Edge> e;
std::vector<int> cur, lv, gap;
int n, s, t;
void bfs() {//分层
for (int i = 1; i <= n; i++)lv[i] = -1;
lv[t] = 0;
gap[0] = 1;
std::queue<int> q;
q.push(t);
while (!q.empty()) {
int x = q.front();
q.pop();
for (int i: v[x]) {
int y = e[i].y;
if (lv[y] == -1) {
lv[y] = lv[x] + 1;
gap[lv[y]]++;
q.push(y);
}
}
}
}
i64 dfs(int x = s, i64 flow = INF) {
if (x == t)return flow;
i64 rmn = flow; // 剩余的流量
for (int i = cur[x]; i < v[x].size() && rmn > 0; i++) // 如果已经没有剩余流量则退出
{
cur[x] = i; // 当前弧优化,更新当前弧
int y = e[v[x][i]].y;
i64 w = e[v[x][i]].w;
if (w > 0 && lv[y] == lv[x] - 1) // 往层数低的方向增广
{
i64 c = dfs(y, std::min(w, rmn)); // 尽可能多地传递流量
rmn -= c; // 剩余流量减少
e[v[x][i]].w -= c; // 更新残余容量
e[v[x][i] ^ 1].w += c;
}
}
if (rmn > 0) {//GAP
gap[lv[x]]--;
if (gap[lv[x]] == 0)lv[s] = n + 1;
lv[x]++;
gap[lv[x]]++;
}
return flow - rmn; // 返回传递出去的流量的大小
}
i64 MaxFlow() {
bfs();
i64 ans = 0;
if (lv[s] == -1)return 0;
while (lv[s] <= n) {
for (int i = 1; i <= n; i++)cur[i] = 0;
ans += dfs();
}
return ans;
}
void solve() {
int m;
std::cin >> n >> m;
s = n * 2 + 1;
t = n * 2 + 2;
for (int i = 1; i <= n * 2 + 2; i++)v[i].clear();
cur.assign(n * 2 + 5, 0);
lv.assign(n * 2 + 5, 0);
gap.assign(n * 2 + 5, 0);
e.clear();
auto AddEdge = [&](int x, int y, i64 w) -> void {
e.emplace_back(x, 0);
v[y].push_back((int) e.size() - 1);
e.emplace_back(y, w);
v[x].push_back((int) e.size() - 1);
};
for (int i = 1; i <= m; i++) {
int x, y;
std::cin >> x >> y;
AddEdge(x, y + n, INF);
}
for (int i = 1; i <= n; i++) {
AddEdge(s, i, 1);
AddEdge(i + n, t, 1);
}
std::vector<bool> vis(n * 2 + 5);
i64 suma = 0, sumb = 0;
auto dfs1 = [&](auto &&self, int x) -> void {
if (x <= n)suma++;
for (int i: v[x]) {
int y = e[i].y;
i64 w = e[i].w;
if (vis[y])continue;
if ((x <= 2 * n && y <= 2 * n) || w > 0) {
vis[y] = true;
self(self, y);
}
}
};
auto dfs2 = [&](auto &&self, int x) -> void {
if (x > n && x <= 2 * n)sumb++;
for (int i: v[x]) {
int y = e[i].y;
i64 w = e[i].w;
if (vis[y])continue;
if ((x <= 2 * n && y <= 2 * n) || w == 0) {
vis[y] = true;
self(self, y);
}
}
};
n = n * 2 + 2;
MaxFlow();
n = (n - 2) / 2;
vis[s] = true;
vis[t] = true;
dfs1(dfs1, s);
vis.assign(n * 2 + 5, false);
vis[s] = true;
vis[t] = true;
dfs2(dfs2, t);
std::cout << suma * sumb << '\n';
}
signed main() {
std::ios::sync_with_stdio(false), std::cin.tie(nullptr);
int T;
std::cin >> T;
while (T--)solve();
}
Details
Tip: Click on the bar to expand more detailed information
Test #1:
score: 100
Accepted
time: 1ms
memory: 3812kb
input:
3 4 3 1 2 3 2 4 3 3 3 1 3 2 2 3 1 3 2 1 2 1 2
output:
6 0 4
result:
ok 3 number(s): "6 0 4"
Test #2:
score: -100
Wrong Answer
time: 4ms
memory: 3612kb
input:
10000 5 4 2 2 3 1 5 3 1 1 1 1 1 1 1 1 1 1 2 2 2 2 1 2 1 1 1 1 1 1 1 1 1 1 1 1 2 3 2 1 1 2 1 1 5 5 1 4 2 2 3 1 1 3 1 2 2 4 2 2 2 1 1 2 1 1 5 1 5 3 3 1 2 2 1 1 1 1 3 2 3 1 2 1 5 2 1 2 2 3 5 3 1 5 4 2 1 2 4 1 1 1 2 3 1 1 2 2 2 1 4 1 1 4 3 1 1 1 1 1 1 1 2 1 2 2 3 3 1 3 2 3 2 2 3 3 1 3 3 3 1 2 3 3 2 2 1 ...
output:
6 0 0 2 0 0 0 0 8 0 16 4 0 6 9 9 9 0 9 4 0 1 1 1 0 4 16 15 3 2 16 0 2 2 20 1 0 0 0 0 16 4 4 16 4 9 0 9 0 2 3 0 9 4 9 16 20 0 0 1 12 0 1 2 0 0 1 0 0 2 2 4 0 12 1 0 0 2 1 2 2 3 0 4 1 6 0 0 0 0 9 16 2 0 1 2 0 12 2 4 0 12 1 1 9 4 6 9 9 12 3 16 15 16 9 4 9 0 1 16 9 9 1 9 16 9 12 4 9 2 0 4 0 6 0 3 0 0 0 0...
result:
wrong answer 9th numbers differ - expected: '6', found: '8'