Skip to content

Commit

Permalink
Merge pull request #21 from mauro3/patch-1
Browse files Browse the repository at this point in the history
Fixes #20
  • Loading branch information
timholy authored Oct 31, 2017
2 parents 9ed3b4f + 1ffad3e commit 502c4d6
Show file tree
Hide file tree
Showing 2 changed files with 44 additions and 17 deletions.
35 changes: 19 additions & 16 deletions src/felzenszwalb.jl
Original file line number Diff line number Diff line change
Expand Up @@ -4,29 +4,29 @@ segments = felzenszwalb(img, k, [min_size])
index_map, num_segments = felzenszwalb(edges, num_vertices, k, [min_size])
```
Segments an image using Felzenszwalb's graph-based algorithm. The function can be used in either of two ways -
Segments an image using Felzenszwalb's graph-based algorithm. The function can be used in either of two ways -
1. `segments = felzenszwalb(img, k, [min_size])`
Segments an image using Felzenszwalb's segmentation algorithm and returns the result as `SegmentedImage`. The algorithm uses
euclidean distance in color space as edge weights for the region adjacency graph.
Parameters:
euclidean distance in color space as edge weights for the region adjacency graph.
Parameters:
- img = input image
- k = Threshold for region merging step. Larger threshold will result in bigger segments.
- min_size = Minimum segment size
2. `index_map, num_segments = felzenszwalb(edges, num_vertices, k, [min_size])`
Segments an image represented as Region Adjacency Graph(RAG) using Felzenszwalb's segmentation algorithm. Each pixel/region
corresponds to a node in the graph and weights on each edge measure the dissimilarity between pixels.
The function returns the number of segments and index mapping from nodes of the RAG to segments.
Parameters:
corresponds to a node in the graph and weights on each edge measure the dissimilarity between pixels.
The function returns the number of segments and index mapping from nodes of the RAG to segments.
Parameters:
- edges = Array of edges in RAG. Each edge is represented as `ImageEdge`.
- num_vertices = Number of vertices in RAG
- k = Threshold for region merging step. Larger threshold will result in bigger segments.
- min_size = Minimum segment size
- min_size = Minimum segment size
"""
Expand Down Expand Up @@ -69,7 +69,7 @@ function felzenszwalb(edges::Array{ImageEdge}, num_vertices::Int, k::Real, min_s
num_sets = length(segments)
segments2index = Dict{Int, Int}()
for i in 1:num_sets
segments2index[segments[i]]=i
segments2index[segments[i]]=i
end

index_map = Array{Int}(num_vertices)
Expand All @@ -80,6 +80,9 @@ function felzenszwalb(edges::Array{ImageEdge}, num_vertices::Int, k::Real, min_s
return index_map, num_sets
end

meantype(::Type{T}) where T = Images.accum(T)
meantype(::Type{T}) where T<:Integer = Float64

function felzenszwalb(img::AbstractArray{T, 2}, k::Real, min_size::Int = 0) where T<:Union{Real,Color}

rows, cols = size(img)
Expand All @@ -95,7 +98,7 @@ function felzenszwalb(img::AbstractArray{T, 2}, k::Real, min_size::Int = 0) wher
if I >= J
continue
end
edges[num] = ImageEdge((I[2]-1)*rows+I[1], (J[2]-1)*rows+J[1], sqrt(sum(abs2,(img[I])-Images.accum(T)(img[J]))))
edges[num] = ImageEdge((I[2]-1)*rows+I[1], (J[2]-1)*rows+J[1], sqrt(sum(abs2,(img[I])-meantype(T)(img[J]))))
num += 1
end
end
Expand All @@ -104,16 +107,16 @@ function felzenszwalb(img::AbstractArray{T, 2}, k::Real, min_size::Int = 0) wher

result = similar(img, Int)
labels = Array(1:num_segments)
region_means = Dict{Int, Images.accum(T)}()
region_means = Dict{Int, meantype(T)}()
region_pix_count = Dict{Int, Int}()

for j in indices(img, 2)
for i in indices(img, 1)
result[i, j] = index_map[(j-1)*rows+i]
region_pix_count[result[i,j]] = get(region_pix_count, result[i, j], 0) + 1
region_means[result[i,j]] = get(region_means, result[i,j], zero(Images.accum(T))) + (img[i, j] - get(region_means, result[i,j], zero(Images.accum(T))))/region_pix_count[result[i,j]]
region_means[result[i,j]] = get(region_means, result[i,j], zero(meantype(T))) + (img[i, j] - get(region_means, result[i,j], zero(meantype(T))))/region_pix_count[result[i,j]]
end
end

return SegmentedImage(result, labels, region_means, region_pix_count)
end
return SegmentedImage(result, labels, region_means, region_pix_count)
end
26 changes: 25 additions & 1 deletion test/felzenszwalb.jl
Original file line number Diff line number Diff line change
Expand Up @@ -47,4 +47,28 @@
@test result.segment_pixel_count[result.image_indexmap[1,1]] == 92
@test result.segment_pixel_count[result.image_indexmap[2,2]] == 4
@test result.segment_pixel_count[result.image_indexmap[5,5]] == 4
end

# issue 20
img = falses(10, 10)
img[2:3, 2:3] = true
img[2, 8] = true
img[5:6, 5:6] = true
T = Bool

result = felzenszwalb(img, 1, 2)

@test length(result.segment_labels) == 3
@test result.segment_labels == collect(1:3)

@test result.image_indexmap[1, 1] == result.image_indexmap[2, 8]
@test all(label->(label==result.image_indexmap[2,2]), result.image_indexmap[2:3, 2:3])
@test all(label->(label==result.image_indexmap[5,5]), result.image_indexmap[5:6, 5:6])

@test result.segment_means[result.image_indexmap[1,1]] 1/92
@test result.segment_means[result.image_indexmap[2,2]] == Images.accum(T)(img[2,2])
@test result.segment_means[result.image_indexmap[5,5]] == Images.accum(T)(img[5,5])

@test result.segment_pixel_count[result.image_indexmap[1,1]] == 92
@test result.segment_pixel_count[result.image_indexmap[2,2]] == 4
@test result.segment_pixel_count[result.image_indexmap[5,5]] == 4
end

0 comments on commit 502c4d6

Please sign in to comment.