最大流问题,只不过该题需要另外新建一个源点和汇点,悲催的是用EdmondsKarp算法超时了,O(nm^2)。 #include <iostream> #include <cstdio> #include <cstring> #include <queue> using namespace std; #define min(a,b) (a<b?a:b) const int inf = 0x7fffffff; class { public: int flow; int capacity; } map[101][101]; int n, np, nc, m; //n节点总数,np发电站数,nc消费者数,m边数 int maxflow, sp, fp; //最大流,源点,汇点 int pre[101]; //用于bfs寻找路径 int bfs(int start, int end) { int a[101]; //用来记录该路径最小边 int u, v; queue<int> q; memset(a, 0, sizeof(a)); memset(pre, -1, sizeof(pre)); q.push(start); a[start] = inf; while (!q.empty()) { u = q.front(); q.pop(); for (v = 1; v <= n; ++v) { if (!a[v] && map[u][v].capacity > map[u][v].flow) { //未标记且有剩余容量 q.push(v); pre[v] = u; a[v] = min(a[u], map[u][v].capacity - map[u][v].flow); } } if (v == end) break; } return a[end]; } void EdmondsKarp() { int tmp; //一条增广路的剩余容量 maxflow = 0; while (tmp = bfs(sp, fp)) { for (int i = fp; i != sp; i = pre[i]) { map[i][pre[i]].flow -= tmp; //更新反向流 map[pre[i]][i].flow += tmp; //更新正向流 } maxflow += tmp; } } int main() { //freopen("temp.txt", "r", stdin); int x, y, z; char tmp; while (cin >> n >> np >> nc >> m) { memset(map, 0, sizeof(map)); for (int i = 1; i <= m; ++i) { cin >> tmp >> x >> tmp >> y >> tmp >> z; map[x+1][y+1].capacity = z; } //新建源点指向所有的发电站 sp = n+1; fp = n+2; n += 2; for (int i = 1; i <= np; ++i) { cin >> tmp >> x >> tmp >> y; map[sp][x+1].capacity = y; } //新建汇点,使所有消费者指向它 for (int i = 1; i <= nc; ++i) { cin >> tmp >> x >> tmp >> y; map[x+1][fp].capacity = y; } EdmondsKarp(); cout << maxflow << endl; } return 0; }