赞
踩
Ford-Fulkerson算法是用于求解最大流问题的一种经典算法。其核心思想是通过不断寻找增广路径来增加流量,直到找不到增广路径为止。每次找到一条增广路径,就增加相应的流量,更新残余网络。简单来说就是Ford-Fulkerson算法的工作过程,即不断寻找增广路径并增加流量,直到无法找到增广路径为止。
以一个简单的例子来演示Ford-Fulkerson算法的执行过程。
假设有一个流网络如下:
- 源点 (S)
- / \
- 10 5
- / \
- A B
- \ /
- 5 10
- \ /
- C
- |
- 10
- |
- 汇点 (T)
其中每条边的数字表示容量。
步骤1:初始化
步骤2:寻找增广路径
步骤3:增广路径上增加流量
步骤4:更新残余网络
步骤2:寻找增广路径(继续)
步骤3:增广路径上增加流量
步骤4:更新残余网络
步骤2:寻找增广路径(结束)
结果
- #include <iostream> // 包含输入输出流的头文件
- #include <vector> // 包含向量容器的头文件
- #include <queue> // 包含队列容器的头文件
- #include <climits> // 包含INT_MAX定义的头文件
- #include <cstring> // 包含memset函数的头文件
-
- using namespace std; // 使用标准命名空间
-
- class FordFulkerson {
- int V; // 顶点数量
- vector<vector<int>> capacity; // 容量矩阵
- vector<vector<int>> adj; // 邻接表
-
- // 广度优先搜索(BFS)函数,用于在残余网络中寻找增广路径
- bool bfs(vector<int>& parent, int s, int t) {
- vector<bool> visited(V, false); // 访问标记数组,初始化为未访问
- queue<int> q; // BFS队列
- q.push(s); // 源点入队
- visited[s] = true; // 标记源点为已访问
- parent[s] = -1; // 源点没有父节点
-
- while (!q.empty()) { // 当队列不为空时
- int u = q.front(); // 取出队首元素
- q.pop(); // 队首元素出队
-
- for (int v : adj[u]) { // 遍历邻接表中的所有邻接节点
- if (!visited[v] && capacity[u][v] > 0) { // 如果节点未访问且有剩余容量
- if (v == t) { // 如果找到汇点
- parent[v] = u; // 记录父节点
- return true; // 返回找到增广路径
- }
- q.push(v); // 将节点入队
- parent[v] = u; // 记录父节点
- visited[v] = true; // 标记节点为已访问
- }
- }
- }
- return false; // 如果没有找到增广路径,返回false
- }
-
- public:
- // 构造函数,初始化顶点数量、容量矩阵和邻接表
- FordFulkerson(int V) : V(V), capacity(V, vector<int>(V, 0)), adj(V) {}
-
- // 添加边及其容量
- void addEdge(int u, int v, int cap) {
- capacity[u][v] = cap; // 设置容量
- adj[u].push_back(v); // 添加邻接点
- adj[v].push_back(u); // 添加反向边的邻接点
- }
-
- // 计算最大流量
- int maxFlow(int s, int t) {
- int max_flow = 0; // 初始化最大流量为0
- vector<int> parent(V); // 用于记录增广路径中的父节点
-
- while (bfs(parent, s, t)) { // 当找到增广路径时
- int path_flow = INT_MAX; // 初始化路径流量为无穷大
-
- // 计算增广路径中的最小流量
- for (int v = t; v != s; v = parent[v]) {
- int u = parent[v];
- path_flow = min(path_flow, capacity[u][v]);
- }
-
- // 更新残余网络中的容量
- for (int v = t; v != s; v = parent[v]) {
- int u = parent[v];
- capacity[u][v] -= path_flow;
- capacity[v][u] += path_flow;
- }
-
- // 增加总流量
- max_flow += path_flow;
- }
-
- return max_flow; // 返回最大流量
- }
- };
-
- int main() {
- int V = 6; // 顶点数量 (包括源点和汇点)
- FordFulkerson graph(V); // 创建一个FordFulkerson对象
-
- // 添加边和对应的容量
- graph.addEdge(0, 1, 10); // S -> A 容量 10
- graph.addEdge(0, 2, 5); // S -> B 容量 5
- graph.addEdge(1, 3, 5); // A -> C 容量 5
- graph.addEdge(2, 3, 10); // B -> C 容量 10
- graph.addEdge(3, 5, 10); // C -> T 容量 10
-
- int source = 0; // 源点 S
- int sink = 5; // 汇点 T
-
- // 计算并输出最大流量
- cout << "最大流量: " << graph.maxFlow(source, sink) << endl;
-
- return 0;
- }
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。