洛谷P3980 志愿者招募
题意:懒得写了......
解:
一开始想的是每天建点,每种人建点,然后连边费用流,发现一个人可以管辖多天,不好处理。
回想起了网络流24题中的"最长k可重线段集","最长k可重区间集"等问题,然后发现这题也可以横着流啊。
具体来说,首先在下面开一条安全快速绿色通道,存放那些不用的人(流量)。
那么每天要用怎么办?把人逼出去!
流量设为INF - ai就可以逼出去ai个人了!
然后每种人都对应一段区间,连边跑最小费用最大流即可。
1 #include <cstdio> 2 #include <algorithm> 3 #include <queue> 4 #include <cstring> 5 6 const int N = 1010, M = 1000010, INF = 0x3f3f3f3f; 7 8 struct Edge { 9 int nex, v, c, len; 10 }edge[M << 1]; int top = 1; 11 12 int e[N], d[N], vis[N], pre[N], flow[N]; 13 std::queue<int> Q; 14 15 inline void add(int x, int y, int z, int w) { 16 top++; 17 edge[top].v = y; 18 edge[top].c = z; 19 edge[top].len = w; 20 edge[top].nex = e[x]; 21 e[x] = top; 22 23 top++; 24 edge[top].v = x; 25 edge[top].c = 0; 26 edge[top].len = -w; 27 edge[top].nex = e[y]; 28 e[y] = top; 29 return; 30 } 31 32 inline bool SPFA(int s, int t) { 33 memset(d, 0x3f, sizeof(d)); 34 d[s] = 0; 35 flow[s] = INF; 36 vis[s] = 1; 37 Q.push(s); 38 while(!Q.empty()) { 39 int x = Q.front(); 40 Q.pop(); 41 vis[x] = 0; 42 for(int i = e[x]; i; i = edge[i].nex) { 43 int y = edge[i].v; 44 if(edge[i].c && d[y] > d[x] + edge[i].len) { 45 d[y] = d[x] + edge[i].len; 46 pre[y] = i; 47 flow[y] = std::min(flow[x], edge[i].c); 48 if(!vis[y]) { 49 vis[y] = 1; 50 Q.push(y); 51 } 52 } 53 } 54 } 55 return d[t] < INF; 56 } 57 58 inline void update(int s, int t) { 59 int temp = flow[t]; 60 while(t != s) { 61 int i = pre[t]; 62 edge[i].c -= temp; 63 edge[i ^ 1].c += temp; 64 t = edge[i ^ 1].v; 65 } 66 return; 67 } 68 69 inline int solve(int s, int t, int &cost) { 70 int ans = 0; 71 cost = 0; 72 while(SPFA(s, t)) { 73 ans += flow[t]; 74 cost += flow[t] * d[t]; 75 update(s, t); 76 } 77 return ans; 78 } 79 80 int main() { 81 int n, m; 82 scanf("%d%d", &n, &m); 83 for(int i = 1, x; i <= n; i++) { 84 scanf("%d", &x); 85 add(i, i + 1, INF - x, 0); 86 } 87 for(int i = 1, x, y, z; i <= m; i++) { 88 scanf("%d%d%d", &x, &y, &z); 89 add(x, y + 1, INF, z); 90 } 91 int s = n + 2; 92 add(s, 1, INF, 0); 93 int ans; 94 solve(s, n + 1, ans); 95 printf("%d", ans); 96 return 0; 97 }
题外话:A了之后我自以为建图很奇葩,跑去看题解,发现都是这种解法......
还可以用线性规划做...好神奇啊。