Skip to content
This repository was archived by the owner on Oct 22, 2021. It is now read-only.

Commit f22cee5

Browse files
authored
Mincut (#11)
* added mincut + tests * added doc
1 parent 2158d81 commit f22cee5

File tree

6 files changed

+82
-2
lines changed

6 files changed

+82
-2
lines changed

docs/make.jl

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,5 +12,6 @@ makedocs(
1212
"Maxflow algorithms" => "maxflow.md",
1313
"Multiroute flows" => "multiroute.md",
1414
"Min-cost flows" => "mincost.md",
15+
"Min-cut" => "mincut.md",
1516
]
1617
)

docs/src/mincut.md

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
## Min-cut
2+
3+
```@autodocs
4+
Modules = [LightGraphsFlows]
5+
Pages = ["mincut.jl"]
6+
Order = [:function, :type]
7+
```

src/LightGraphsFlows.jl

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,9 +19,10 @@ include("multiroute_flow.jl")
1919
include("kishimoto.jl")
2020
include("ext_multiroute_flow.jl")
2121
include("mincost.jl")
22+
include("mincut.jl")
2223

2324
export
2425
maximum_flow, EdmondsKarpAlgorithm, DinicAlgorithm, BoykovKolmogorovAlgorithm, PushRelabelAlgorithm,
25-
multiroute_flow, KishimotoAlgorithm, ExtendedMultirouteFlowAlgorithm, mincost_flow
26+
multiroute_flow, KishimotoAlgorithm, ExtendedMultirouteFlowAlgorithm, mincost_flow, mincut
2627

2728
end

src/mincut.jl

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
"""
2+
mincut(flow_graph::lg.IsDirected, source::Integer, target::Integer, capacity_matrix::AbstractMatrix, algorithm::AbstractFlowAlgorithm)
3+
4+
Compute the min-cut between `source` and `target` for the given graph.
5+
First computes the maxflow using `algorithm` and then builds the partition of the residual graph
6+
Returns a triplet `(part1, part2, flow)` with the partition containing the source, the partition containing the target (the rest) and the min-cut(max-flow) value
7+
"""
8+
function mincut(
9+
flow_graph::lg.DiGraph, # the input graph
10+
source::Integer, # the source vertex
11+
target::Integer, # the target vertex
12+
capacity_matrix::AbstractMatrix, # edge flow capacities
13+
algorithm::AbstractFlowAlgorithm # keyword argument for algorithm
14+
)
15+
flow, flow_matrix = maximum_flow(flow_graph, source, target, capacity_matrix, algorithm)
16+
residual_matrix = spzeros(lg.nv(flow_graph),lg.nv(flow_graph))
17+
for edge in lg.edges(flow_graph)
18+
residual_matrix[edge.src,edge.dst] = max(0.0, capacity_matrix[edge.src,edge.dst] - flow_matrix[edge.src,edge.dst])
19+
end
20+
part1 = typeof(source)[]
21+
queue = [source]
22+
while !isempty(queue)
23+
node = pop!(queue)
24+
push!(part1, node)
25+
dests = [dst for dst in 1:lg.nv(flow_graph) if residual_matrix[node,dst]>0.0 && dst part1]
26+
append!(queue, dests)
27+
end
28+
part2 = [node for node in 1:lg.nv(flow_graph) if node part1]
29+
return (part1, part2, flow)
30+
end

test/mincut.jl

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
@testset "Mincut" begin
2+
3+
g = lg.CompleteDiGraph(5)
4+
cap1 = [
5+
0.0 2.0 2.0 0.0 0.0
6+
0.0 0.0 0.0 0.0 3.0
7+
0.0 1.0 0.0 3.0 0.0
8+
0.0 0.0 0.0 0.0 1.0
9+
0.0 0.0 0.0 0.0 0.0
10+
];
11+
(part1, part2, value) = LightGraphsFlows.mincut(g,1,5,cap1,LightGraphsFlows.PushRelabelAlgorithm())
12+
@test value 4.0
13+
@test part1 == [1]
14+
@test sort(part2) == collect(2:5)
15+
cap2 = [
16+
0.0 3.0 2.0 0.0 0.0
17+
0.0 0.0 0.0 0.0 3.0
18+
0.0 1.0 0.0 3.0 0.0
19+
0.0 0.0 0.0 0.0 1.5
20+
0.0 0.0 0.0 0.0 0.0
21+
];
22+
(part1, part2, value) = LightGraphsFlows.mincut(g,1,5,cap2,LightGraphsFlows.PushRelabelAlgorithm())
23+
@test value 4.5
24+
@test sort(part1) == collect(1:4)
25+
@test part2 == [5]
26+
27+
g2 = lg.DiGraph(5)
28+
lg.add_edge!(g2,1,2)
29+
lg.add_edge!(g2,1,3)
30+
lg.add_edge!(g2,3,4)
31+
lg.add_edge!(g2,3,2)
32+
lg.add_edge!(g2,2,5)
33+
34+
(part1, part2, value) = LightGraphsFlows.mincut(g2,1,5,cap1,LightGraphsFlows.PushRelabelAlgorithm())
35+
@test value 3.0
36+
@test sort(part1) == [1,3,4]
37+
@test sort(part2) == [2,5]
38+
39+
end

test/runtests.jl

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,9 @@ for t in [
1616
"push_relabel",
1717
"maximum_flow",
1818
"multiroute_flow",
19-
"mincost"]
19+
"mincost",
20+
"mincut",
21+
]
2022
tp = joinpath(testdir, "$(t).jl")
2123
include(tp)
2224
end

0 commit comments

Comments
 (0)