P3358 最长k可重区间集问题
#include <bits/stdc++.h>
using namespace std;
typedef pair<int, int> P;
struct edge {
int to, cap, cost, rev;
edge(int a, int b, int c, int d)
: to(a), cap(b), cost(c), rev(d) {}
};
const int maxn = 510;
const int maxv = maxn * 2;
const int inf = 0x3f3f3f3f;
int cas;
int n, k, m;
int A[maxn], B[maxn], C[maxn];
vector<int> X;
vector<edge> G[maxv];
int dis0[maxv], dis1[maxv];
int pv[maxv], pe[maxv];
void add(int from, int to, int cap, int cost) {
G[from].push_back(edge(to, cap, cost, G[to].size()));
G[to].push_back(edge(from, 0, -cost, G[from].size() - 1));
}
//迪杰斯特拉算法求最短路
void dijkstra(int s) {
memset(dis1, inf, sizeof dis1);
dis1[s] = 0;
priority_queue<P, vector<P>, greater<P> > qu;
qu.push(P(0, s));
while (qu.size()) {
P p = qu.top();
qu.pop();
int v = p.second;
if (dis1[v] < p.first) continue;
for (int i = 0; i < G[v].size(); i++) {
edge e = G[v][i];
if (e.cap > 0 && dis1[e.to] > dis1[v] + e.cost + dis0[v] - dis0[e.to]) {
dis1[e.to] = dis1[v] + e.cost + dis0[v] - dis0[e.to];
pv[e.to] = v;
pe[e.to] = i;
qu.push(P(dis1[e.to], e.to));
}
}
}
}
//最小费用流算法
int min_cost_flow(int s, int t, int f) {
int res = 0;
memset(dis0, 0, sizeof dis0);
while (f > 0) {
dijkstra(s);
if (dis1[t] == inf) return -1;
for (int i = s; i <= t; i++)
dis0[i] += dis1[i];
int d = f;
for (int v = t; v != s; v = pv[v])
d = min(d, G[pv[v]][pe[v]].cap);
f -= d;
res += d * dis0[t];
for (int v = t; v != s; v = pv[v]) {
edge &e = G[pv[v]][pe[v]];
e.cap -= d;
G[e.to][e.rev].cap += d;
}
}
return res;
}
int main() {
X.clear();
for (int i = 0; i < maxv; i++)
G[i].clear();
cin >> n >> k;
for (int i = 0; i < n; i++) {
cin >> A[i] >> B[i];
C[i] = B[i] - A[i];
X.push_back(A[i]);
X.push_back(B[i]);
}
//离散化
sort(X.begin(), X.end());
X.erase(unique(X.begin(), X.end()), X.end());
int s = 0, t = X.size() - 1;
for (int i = 0; i < t; i++)
add(i, i + 1, inf, 0);
for (int i = 0; i < n; i++) {
int a = lower_bound(X.begin(), X.end(), A[i]) - X.begin();
int b = lower_bound(X.begin(), X.end(), B[i]) - X.begin();
add(a, b, 1, -C[i]);
}
cout << -min_cost_flow(s, t, k) << endl;
return 0;
}
原文地址:https://www.cnblogs.com/albert-biu/p/11291644.html
时间: 2024-10-08 11:33:27