【题目链接】
【思路要点】
- 补档博客,无题解。
【代码】
#include<bits/stdc++.h>
using namespace std;
#define MAXN 5005
#define MAXQ 1000005
#define INF 1e9
template <typename T> void read(T &x) {
x = 0; int f = 1;
char c = getchar();
for (; !isdigit(c); c = getchar()) if (c == '-') f = -f;
for (; isdigit(c); c = getchar()) x = x * 10 + c - '0';
x *= f;
}
struct edge {int dest, flow, cost; unsigned home; };
vector <edge> a[MAXN];
int n, m, s, t, len, flow, cost;
int dist[MAXN], path[MAXN];
unsigned home[MAXN];
void flow_path() {
int p = t, ans = INF;
while (p != s) {
ans = min(ans, a[path[p]][home[p]].flow);
p = path[p];
}
flow += ans, cost += ans * len;
p = t;
while (p != s) {
a[path[p]][home[p]].flow -= ans;
a[p][a[path[p]][home[p]].home].flow += ans;
p = path[p];
}
}
bool spfa() {
static int q[MAXQ];
static bool inq[MAXN];
int l = 0, r = 0;
q[0] = s, inq[s] = true, dist[s] = 0;
while (l <= r) {
int tmp = q[l++];
inq[tmp] = false;
for (unsigned i = 0; i < a[tmp].size(); i++)
if (a[tmp][i].flow != 0 && dist[a[tmp][i].dest] > dist[tmp] + a[tmp][i].cost) {
dist[a[tmp][i].dest] = dist[tmp] + a[tmp][i].cost;
path[a[tmp][i].dest] = tmp;
home[a[tmp][i].dest] = i;
if (!inq[a[tmp][i].dest]) {
inq[a[tmp][i].dest] = true;
q[++r] = a[tmp][i].dest;
}
}
}
len = dist[t];
for (int i = 0; i <= r; i++)
dist[q[i]] = INF;
return len != INF;
}
void addedge(int x, int y, int flow, int cost) {
a[x].push_back((edge) {y, flow, cost, a[y].size()});
a[y].push_back((edge) {x, 0, -cost, a[x].size() - 1});
}
int main() {
read(n), read(m);
s = 0, t = 2 * n + 1;
for (int i = 1; i <= n; i++) {
addedge(s, i, 1, 0);
addedge(i + n, t, 1, 0);
}
for (int i = 1; i <= n; i++) {
int x; read(x);
addedge(s, i + n, 1, x);
}
for (int i = 1; i <= m; i++) {
int x, y, z;
read(x), read(y), read(z);
if (x > y) swap(x, y);
addedge(x, y + n, 1, z);
}
for (int i = s; i <= t; i++)
dist[i] = INF;
while (spfa())
flow_path();
printf("%d\n", cost);
return 0;
}