Skip to content
GitLab
Menu
Projects
Groups
Snippets
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Menu
Open sidebar
Olena
pylene
Commits
25a92452
Commit
25a92452
authored
Oct 11, 2019
by
Edwin Carlinet
Browse files
Migration of Local Extremum Labelization Algorithm
parent
8b2196cb
Changes
12
Show whitespace changes
Inline
Side-by-side
.clang-format
View file @
25a92452
...
...
@@ -25,8 +25,7 @@ BraceWrapping:
NamespaceIndentation: All
FixNamespaceComments: true
IndentWrappedFunctionNames: true
# AllowShortFunctionsOnASingleLine: None
IndentWrappedFunctionNames: false # Do not indent after function def break
AllowShortFunctionsOnASingleLine: Inline
AlwaysBreakTemplateDeclarations: true
AlignAfterOpenBracket: Align
...
...
bench/BMMorphoBase.cpp
View file @
25a92452
...
...
@@ -16,6 +16,8 @@
#include
<mln/morpho/experimental/opening.hpp>
#include
<mln/morpho/experimental/reconstruction.hpp>
#include
<mln/labeling/experimental/local_extrema.hpp>
#include
<benchmark/benchmark.h>
#include
<fixtures/ImagePath/image_path.hpp>
...
...
@@ -203,4 +205,15 @@ BENCHMARK_F(BMMorpho, Hit_or_miss_corner)(benchmark::State& st)
}
BENCHMARK_F
(
BMMorpho
,
minima
)(
benchmark
::
State
&
st
)
{
auto
f
=
[](
const
image_t
&
input
,
image_t
&
)
{
int
nlabel
;
mln
::
labeling
::
experimental
::
local_minima
<
int8_t
>
(
input
,
mln
::
experimental
::
c4
,
nlabel
);
return
nlabel
;
};
this
->
run
(
st
,
f
);
}
BENCHMARK_MAIN
();
bench/BMMorphoBaseRef.cpp
View file @
25a92452
...
...
@@ -16,6 +16,8 @@
#include
<mln/morpho/structural/erode.hpp>
#include
<mln/morpho/structural/opening.hpp>
#include
<mln/labeling/local_extrema.hpp>
// [legacy]
#include
<mln/core/image/image2d.hpp>
...
...
@@ -150,5 +152,15 @@ BENCHMARK_F(BMMorpho, Hit_or_miss_corner)(benchmark::State& st)
this
->
run
(
st
,
f
);
}
BENCHMARK_F
(
BMMorpho
,
minima
)(
benchmark
::
State
&
st
)
{
auto
f
=
[](
const
image_t
&
input
,
image_t
&
)
{
int
nlabel
;
mln
::
labeling
::
local_minima
<
int8_t
>
(
input
,
mln
::
c4
,
nlabel
);
return
nlabel
;
};
this
->
run
(
st
,
f
);
}
BENCHMARK_MAIN
();
bench/CMakeLists.txt
View file @
25a92452
...
...
@@ -25,10 +25,10 @@ ExternalData_Expand_Arguments(
if
(
CMAKE_CXX_COMPILER_ID STREQUAL
"Clang"
)
set
(
STANDALONE_COMPILE_FLAGS
"-Rpass=loop-vectorize -Rpass-missed=loop-vectorize -Rpass-analysis=loop-vectorize -gline-tables-only -gcolumn-info "
)
set
(
CMAKE_CXX_FLAGS_RELEASE
"
${
CMAKE_CXX_FLAGS_RELEASE
}
-O3 -march=native"
)
set
(
CMAKE_CXX_FLAGS_RELEASE
"
${
CMAKE_CXX_FLAGS_RELEASE
}
-O3 -march=native
-g
"
)
elseif
(
CMAKE_CXX_COMPILER_ID STREQUAL
"GNU"
)
set
(
STANDALONE_COMPILE_FLAGS
"-g -fopt-info -fopt-info-vec-missed -ftree-vectorize -ftree-vectorizer-verbose=2"
)
set
(
CMAKE_CXX_FLAGS_RELEASE
"
${
CMAKE_CXX_FLAGS_RELEASE
}
-O3 -march=native"
)
set
(
STANDALONE_COMPILE_FLAGS
"-g -fopt-info
-vec
-fopt-info-vec-missed -ftree-vectorize -ftree-vectorizer-verbose=2"
)
set
(
CMAKE_CXX_FLAGS_RELEASE
"
${
CMAKE_CXX_FLAGS_RELEASE
}
-O3 -march=native
-g
"
)
else
()
# W4141: 'inline' : utilisé plusieurs fois in benchmark.h
set
(
STANDALONE_COMPILE_FLAGS
" "
)
...
...
pylene/include/mln/core/image/experimental/private/ndbuffer_image.hpp
View file @
25a92452
...
...
@@ -203,7 +203,7 @@ namespace mln
/******************************************/
template
<
class
T
,
int
N
>
experimental
::
ndbox
<
N
>
__ndbuffer_image
<
T
,
N
>::
domain
()
const
noexcept
inline
experimental
::
ndbox
<
N
>
__ndbuffer_image
<
T
,
N
>::
domain
()
const
noexcept
{
experimental
::
ndpoint
<
N
>
pmin
,
pmax
;
for
(
int
k
=
0
;
k
<
N
;
++
k
)
...
...
@@ -216,20 +216,21 @@ namespace mln
template
<
class
T
,
int
N
>
void
__ndbuffer_image
<
T
,
N
>::
__init
(
alloc_fun_t
__allocate
,
int
topleft
[],
int
sizes
[],
std
::
ptrdiff_t
byte_strides
[],
inline
void
__ndbuffer_image
<
T
,
N
>::
__init
(
alloc_fun_t
__allocate
,
int
topleft
[],
int
sizes
[],
std
::
ptrdiff_t
byte_strides
[],
const
image_build_params
&
params
)
{
base
::
__init
(
__allocate
,
sample_type_traits
<
T
>::
id
(),
sizeof
(
T
),
N
,
topleft
,
sizes
,
byte_strides
,
params
);
}
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
concretize
()
const
noexcept
->
image_builder
<
concrete_type
,
__ndbuffer_image
<
T
,
N
>>
inline
auto
__ndbuffer_image
<
T
,
N
>::
concretize
()
const
noexcept
->
image_builder
<
concrete_type
,
__ndbuffer_image
<
T
,
N
>>
{
return
{
*
this
};
}
template
<
class
T
,
int
N
>
template
<
class
V
>
inline
auto
__ndbuffer_image
<
T
,
N
>::
ch_value
()
const
noexcept
->
image_builder
<
ch_value_type
<
V
>
,
__ndbuffer_image
<
T
,
N
>>
{
return
{
*
this
};
...
...
@@ -237,7 +238,7 @@ namespace mln
template
<
class
T
,
int
N
>
__ndbuffer_image
<
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
from_buffer
(
T
*
buffer
,
int
topleft
[],
int
sizes
[],
inline
__ndbuffer_image
<
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
from_buffer
(
T
*
buffer
,
int
topleft
[],
int
sizes
[],
std
::
ptrdiff_t
byte_strides
[],
bool
copy
)
{
image_build_params
params
;
...
...
@@ -264,7 +265,7 @@ namespace mln
}
template
<
class
T
,
int
N
>
__ndbuffer_image
<
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
from_buffer
(
T
*
buffer
,
int
sizes
[],
std
::
ptrdiff_t
byte_strides
[],
bool
copy
)
inline
__ndbuffer_image
<
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
from_buffer
(
T
*
buffer
,
int
sizes
[],
std
::
ptrdiff_t
byte_strides
[],
bool
copy
)
{
int
topleft
[
N
]
=
{
0
};
return
__ndbuffer_image
<
T
,
N
>::
from_buffer
(
buffer
,
topleft
,
sizes
,
byte_strides
,
copy
);
...
...
@@ -272,7 +273,7 @@ namespace mln
template
<
class
T
,
int
N
>
template
<
class
E
>
__ndbuffer_image
<
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
from
(
const
mln
::
ndimage_base
<
T
,
N
,
E
>&
other
)
inline
__ndbuffer_image
<
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
from
(
const
mln
::
ndimage_base
<
T
,
N
,
E
>&
other
)
{
auto
tmp
=
base
::
from
(
other
);
return
static_cast
<
__ndbuffer_image
&>
(
tmp
);
...
...
@@ -280,20 +281,20 @@ namespace mln
template
<
class
T
,
int
N
>
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
experimental
::
ndbox
<
N
>
domain
,
const
image_build_params
&
params
)
inline
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
experimental
::
ndbox
<
N
>
domain
,
const
image_build_params
&
params
)
{
this
->
resize
(
domain
,
params
);
}
template
<
class
T
,
int
N
>
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
()
inline
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
()
:
base
(
details
::
ndbuffer_image_info_t
{
sample_type_traits
<
T
>::
id
(),
N
,
{},
nullptr
})
{
}
template
<
class
T
,
int
N
>
template
<
int
,
class
>
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
int
width
,
const
image_build_params
&
params
)
inline
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
int
width
,
const
image_build_params
&
params
)
{
this
->
resize
(
width
,
params
);
}
...
...
@@ -301,14 +302,14 @@ namespace mln
template
<
class
T
,
int
N
>
template
<
int
,
class
>
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
int
width
,
int
height
,
const
image_build_params
&
params
)
inline
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
int
width
,
int
height
,
const
image_build_params
&
params
)
{
this
->
resize
(
width
,
height
,
params
);
}
template
<
class
T
,
int
N
>
template
<
int
,
class
>
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
int
width
,
int
height
,
int
depth
,
const
image_build_params
&
params
)
inline
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
int
width
,
int
height
,
int
depth
,
const
image_build_params
&
params
)
{
this
->
resize
(
width
,
height
,
depth
,
params
);
}
...
...
@@ -316,21 +317,21 @@ namespace mln
template
<
class
T
,
int
N
>
template
<
int
M
,
class
>
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
std
::
initializer_list
<
T
>
values
)
inline
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
std
::
initializer_list
<
T
>
values
)
:
base
(
std
::
move
(
values
))
{
}
template
<
class
T
,
int
N
>
template
<
int
M
,
class
>
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
std
::
initializer_list
<
std
::
initializer_list
<
T
>>
values
)
inline
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
std
::
initializer_list
<
std
::
initializer_list
<
T
>>
values
)
:
base
(
std
::
move
(
values
))
{
}
template
<
class
T
,
int
N
>
template
<
int
M
,
class
>
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
inline
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
std
::
initializer_list
<
std
::
initializer_list
<
std
::
initializer_list
<
T
>>>
values
)
:
base
(
std
::
move
(
values
))
{
...
...
@@ -339,13 +340,13 @@ namespace mln
template
<
class
T
,
int
N
>
template
<
class
U
>
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
const
__ndbuffer_image
<
U
,
N
>&
other
,
const
image_build_params
&
params
)
inline
__ndbuffer_image
<
T
,
N
>::
__ndbuffer_image
(
const
__ndbuffer_image
<
U
,
N
>&
other
,
const
image_build_params
&
params
)
{
this
->
resize
(
other
,
params
);
}
template
<
class
T
,
int
N
>
void
__ndbuffer_image
<
T
,
N
>::
resize
(
experimental
::
ndbox
<
N
>
domain
,
const
image_build_params
&
params
)
inline
void
__ndbuffer_image
<
T
,
N
>::
resize
(
experimental
::
ndbox
<
N
>
domain
,
const
image_build_params
&
params
)
{
int
tl
[
N
];
int
sz
[
N
];
...
...
@@ -362,7 +363,7 @@ namespace mln
template
<
class
T
,
int
N
>
template
<
int
,
class
>
void
__ndbuffer_image
<
T
,
N
>::
resize
(
int
width
,
const
image_build_params
&
params
)
inline
void
__ndbuffer_image
<
T
,
N
>::
resize
(
int
width
,
const
image_build_params
&
params
)
{
auto
domain
=
experimental
::
ndbox
<
N
>
(
width
);
resize
(
domain
,
params
);
...
...
@@ -371,7 +372,7 @@ namespace mln
template
<
class
T
,
int
N
>
template
<
int
,
class
>
void
__ndbuffer_image
<
T
,
N
>::
resize
(
int
width
,
int
height
,
const
image_build_params
&
params
)
inline
void
__ndbuffer_image
<
T
,
N
>::
resize
(
int
width
,
int
height
,
const
image_build_params
&
params
)
{
auto
domain
=
experimental
::
ndbox
<
N
>
(
width
,
height
);
resize
(
domain
,
params
);
...
...
@@ -380,7 +381,7 @@ namespace mln
template
<
class
T
,
int
N
>
template
<
int
,
class
>
void
__ndbuffer_image
<
T
,
N
>::
resize
(
int
width
,
int
height
,
int
depth
,
const
image_build_params
&
params
)
inline
void
__ndbuffer_image
<
T
,
N
>::
resize
(
int
width
,
int
height
,
int
depth
,
const
image_build_params
&
params
)
{
auto
domain
=
experimental
::
ndbox
<
N
>
(
width
,
height
,
depth
);
resize
(
domain
,
params
);
...
...
@@ -389,7 +390,7 @@ namespace mln
template
<
class
T
,
int
N
>
template
<
class
U
>
void
__ndbuffer_image
<
T
,
N
>::
resize
(
const
__ndbuffer_image
<
U
,
N
>&
other
,
image_build_params
params
)
inline
void
__ndbuffer_image
<
T
,
N
>::
resize
(
const
__ndbuffer_image
<
U
,
N
>&
other
,
image_build_params
params
)
{
if
(
params
.
border
==
-
1
)
params
.
border
=
other
.
border
();
...
...
@@ -400,7 +401,7 @@ namespace mln
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
point_at_index
(
index_type
i
)
const
noexcept
->
point_type
inline
auto
__ndbuffer_image
<
T
,
N
>::
point_at_index
(
index_type
i
)
const
noexcept
->
point_type
{
point_type
coords
;
Impl
::
get_point
(
this
->
__info
(),
i
,
coords
.
data
());
...
...
@@ -408,7 +409,7 @@ namespace mln
}
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
index_of_point
(
point_type
p
)
const
noexcept
->
index_type
inline
auto
__ndbuffer_image
<
T
,
N
>::
index_of_point
(
point_type
p
)
const
noexcept
->
index_type
{
assert
(
Impl
::
is_point_valid
(
this
->
__info
(),
p
.
data
()));
return
Impl
::
get_index
(
this
->
__info
(),
p
.
data
());
...
...
@@ -416,25 +417,25 @@ namespace mln
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
delta_index
(
point_type
p
)
const
noexcept
->
index_type
inline
auto
__ndbuffer_image
<
T
,
N
>::
delta_index
(
point_type
p
)
const
noexcept
->
index_type
{
return
Impl
::
get_index
(
this
->
__info
(),
p
.
data
());
}
template
<
class
T
,
int
N
>
T
*
__ndbuffer_image
<
T
,
N
>::
buffer
()
noexcept
inline
T
*
__ndbuffer_image
<
T
,
N
>::
buffer
()
noexcept
{
return
reinterpret_cast
<
T
*>
(
this
->
base
::
buffer
());
}
template
<
class
T
,
int
N
>
const
T
*
__ndbuffer_image
<
T
,
N
>::
buffer
()
const
noexcept
inline
const
T
*
__ndbuffer_image
<
T
,
N
>::
buffer
()
const
noexcept
{
return
reinterpret_cast
<
T
*>
(
this
->
base
::
buffer
());
}
template
<
class
T
,
int
N
>
__ndbuffer_image
<
T
,
2
>
__ndbuffer_image
<
T
,
N
>::
slice
(
int
z
)
const
inline
__ndbuffer_image
<
T
,
2
>
__ndbuffer_image
<
T
,
N
>::
slice
(
int
z
)
const
{
int
begin
[
N
]
=
{
this
->
__axes
(
0
).
domain_begin
,
this
->
__axes
(
1
).
domain_begin
,
z
};
int
end
[
N
]
=
{
this
->
__axes
(
0
).
domain_end
,
this
->
__axes
(
1
).
domain_end
,
z
+
1
};
...
...
@@ -450,7 +451,7 @@ namespace mln
}
template
<
class
T
,
int
N
>
__ndbuffer_image
<
T
,
1
>
__ndbuffer_image
<
T
,
N
>::
row
(
int
y
)
const
inline
__ndbuffer_image
<
T
,
1
>
__ndbuffer_image
<
T
,
N
>::
row
(
int
y
)
const
{
int
begin
[
N
]
=
{
m_axes
[
0
].
domain_begin
,
y
};
int
end
[
N
]
=
{
m_axes
[
0
].
domain_end
,
y
+
1
};
...
...
@@ -466,7 +467,7 @@ namespace mln
}
template
<
class
T
,
int
N
>
__ndbuffer_image
<
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
clip
(
const
experimental
::
ndbox
<
N
>&
roi
)
const
inline
__ndbuffer_image
<
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
clip
(
const
experimental
::
ndbox
<
N
>&
roi
)
const
{
__ndbuffer_image
tmp
=
*
this
;
Impl
::
select
(
&
tmp
,
N
,
roi
.
tl
().
data
(),
roi
.
br
().
data
());
...
...
@@ -475,21 +476,21 @@ namespace mln
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
operator
()(
point_type
p
)
const
noexcept
->
const_reference
inline
auto
__ndbuffer_image
<
T
,
N
>::
operator
()(
point_type
p
)
const
noexcept
->
const_reference
{
assert
(
Impl
::
is_point_in_domain
(
this
->
__info
(),
p
.
data
()));
return
*
Impl
::
get_pointer
(
this
->
__info
(),
p
.
data
());
}
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
operator
()(
point_type
p
)
noexcept
->
reference
inline
auto
__ndbuffer_image
<
T
,
N
>::
operator
()(
point_type
p
)
noexcept
->
reference
{
assert
(
Impl
::
is_point_in_domain
(
this
->
__info
(),
p
.
data
()));
return
*
Impl
::
get_pointer
(
this
->
__info
(),
p
.
data
());
}
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
__pixel_at
(
point_type
p
)
const
noexcept
->
new_const_pixel_type
inline
auto
__ndbuffer_image
<
T
,
N
>::
__pixel_at
(
point_type
p
)
const
noexcept
->
new_const_pixel_type
{
point_type
lcoords
=
p
;
lcoords
[
0
]
=
0
;
...
...
@@ -498,7 +499,7 @@ namespace mln
}
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
__pixel_at
(
point_type
p
)
noexcept
->
new_pixel_type
inline
auto
__ndbuffer_image
<
T
,
N
>::
__pixel_at
(
point_type
p
)
noexcept
->
new_pixel_type
{
point_type
lcoords
=
p
;
lcoords
[
0
]
=
0
;
...
...
@@ -507,62 +508,62 @@ namespace mln
}
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
new_pixel
(
point_type
p
)
const
noexcept
->
new_const_pixel_type
inline
auto
__ndbuffer_image
<
T
,
N
>::
new_pixel
(
point_type
p
)
const
noexcept
->
new_const_pixel_type
{
assert
(
Impl
::
is_point_in_domain
(
this
->
__info
(),
p
.
data
()));
return
this
->
__pixel_at
(
p
);
}
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
new_pixel
(
point_type
p
)
noexcept
->
new_pixel_type
inline
auto
__ndbuffer_image
<
T
,
N
>::
new_pixel
(
point_type
p
)
noexcept
->
new_pixel_type
{
assert
(
Impl
::
is_point_in_domain
(
this
->
__info
(),
p
.
data
()));
return
this
->
__pixel_at
(
p
);
}
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
new_pixel_at
(
point_type
p
)
const
noexcept
->
new_const_pixel_type
inline
auto
__ndbuffer_image
<
T
,
N
>::
new_pixel_at
(
point_type
p
)
const
noexcept
->
new_const_pixel_type
{
assert
(
Impl
::
is_point_valid
(
this
->
__info
(),
p
.
data
()));
return
this
->
__pixel_at
(
p
);
}
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
new_pixel_at
(
point_type
p
)
noexcept
->
new_pixel_type
inline
auto
__ndbuffer_image
<
T
,
N
>::
new_pixel_at
(
point_type
p
)
noexcept
->
new_pixel_type
{
assert
(
Impl
::
is_point_valid
(
this
->
__info
(),
p
.
data
()));
return
this
->
__pixel_at
(
p
);
}
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
at
(
point_type
p
)
const
noexcept
->
const_reference
inline
auto
__ndbuffer_image
<
T
,
N
>::
at
(
point_type
p
)
const
noexcept
->
const_reference
{
assert
(
Impl
::
is_point_valid
(
this
->
__info
(),
p
.
data
()));
return
*
Impl
::
get_pointer
(
this
->
__info
(),
p
.
data
());
}
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
at
(
point_type
p
)
noexcept
->
reference
inline
auto
__ndbuffer_image
<
T
,
N
>::
at
(
point_type
p
)
noexcept
->
reference
{
assert
(
Impl
::
is_point_valid
(
this
->
__info
(),
p
.
data
()));
return
*
Impl
::
get_pointer
(
this
->
__info
(),
p
.
data
());
}
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
operator
[](
index_type
i
)
const
noexcept
->
const_reference
inline
auto
__ndbuffer_image
<
T
,
N
>::
operator
[](
index_type
i
)
const
noexcept
->
const_reference
{
return
*
Impl
::
get_pointer
(
this
->
__info
(),
i
);
}
template
<
class
T
,
int
N
>
auto
__ndbuffer_image
<
T
,
N
>::
operator
[](
index_type
i
)
noexcept
->
reference
inline
auto
__ndbuffer_image
<
T
,
N
>::
operator
[](
index_type
i
)
noexcept
->
reference
{
return
*
Impl
::
get_pointer
(
this
->
__info
(),
i
);
}
template
<
class
T
,
int
N
>
ranges
::
multi_span
<
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
new_values
()
noexcept
inline
ranges
::
multi_span
<
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
new_values
()
noexcept
{
std
::
array
<
std
::
size_t
,
N
>
counts
;
std
::
array
<
std
::
ptrdiff_t
,
N
>
strides
;
...
...
@@ -575,7 +576,7 @@ namespace mln
}
template
<
class
T
,
int
N
>
ranges
::
multi_span
<
const
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
new_values
()
const
noexcept
inline
ranges
::
multi_span
<
const
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
new_values
()
const
noexcept
{
std
::
array
<
std
::
size_t
,
N
>
counts
;
std
::
array
<
std
::
ptrdiff_t
,
N
>
strides
;
...
...
@@ -589,14 +590,14 @@ namespace mln
template
<
class
T
,
int
N
>
experimental
::
details
::
ndpix_range
<
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
new_pixels
()
noexcept
inline
experimental
::
details
::
ndpix_range
<
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
new_pixels
()
noexcept
{
return
{
this
->
__info
()};
}
template
<
class
T
,
int
N
>
experimental
::
details
::
ndpix_range
<
const
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
new_pixels
()
const
noexcept
inline
experimental
::
details
::
ndpix_range
<
const
T
,
N
>
__ndbuffer_image
<
T
,
N
>::
new_pixels
()
const
noexcept
{
return
{
this
->
__info
()};
}
...
...
pylene/include/mln/core/image/experimental/private/ndbuffer_image_impl.hpp
View file @
25a92452
...
...
@@ -125,7 +125,6 @@ namespace mln::details
}
template
<
int
pdim
>
void
*
ndbuffer_image_impl_base_2
<
pdim
>::
get_pointer
(
const
ndbuffer_image_info_t
*
ima
,
const
int
coordinates
[])
{
...
...
@@ -135,14 +134,22 @@ namespace mln::details
return
ima
->
m_buffer
+
x
;
}
// Return a pointer to the loc given by p
template
<
class
T
,
int
pdim
>
T
*
ndbuffer_image_impl
<
T
,
pdim
>::
get_pointer
(
const
ndbuffer_image_info_t
*
ima
,
const
int
coordinates
[])
{
if
constexpr
(
std
::
is_same_v
<
T
,
void
>
)
return
reinterpret_cast
<
T
*>
(
ndbuffer_image_impl_base_2
<
pdim
>::
get_pointer
(
ima
,
coordinates
));
else
{
std
::
ptrdiff_t
x
=
0
;
for
(
int
k
=
1
;
k
<
get_pdim
(
ima
);
++
k
)
x
+=
coordinates
[
k
]
*
ima
->
m_axes
[
k
].
byte_stride
;
return
reinterpret_cast
<
T
*>
(
ima
->
m_buffer
+
x
)
+
coordinates
[
0
];
}
}
template
<
class
T
>
T
*
ndbuffer_image_impl_base_1
<
T
>::
get_pointer
(
const
ndbuffer_image_info_t
*
ima
,
std
::
ptrdiff_t
index
)
{
...
...
pylene/include/mln/core/image/view/clip.hpp
View file @
25a92452
...
...
@@ -20,6 +20,9 @@ namespace mln
{
D
m_subdomain
;
template
<
class
I2
,
class
D2
>
friend
class
clip_view
;
public:
/// Type definitions
/// \{
...
...
@@ -60,14 +63,7 @@ namespace mln
template
<
class
I2
,
class
D2
>
clip_view
(
const
clip_view
<
I2
,
D2
>&
other
,
const
image_build_params
&
params
)
:
clip_view
::
image_adaptor
{
imchvalue
<
value_type
>
(
other
,
params
).
build
()}
,
m_subdomain
{
other
.
m_subdomain
}
{
}
template
<
class
I2
,
class
D2
>
clip_view
(
const
clip_view
<
I2
,
D2
>&
other
,
const
value_type
&
v
)
:
clip_view
::
image_adaptor
{
static_cast
<
I
>
((
other
.
base
().
template
ch_value
<
value_type
>()).
init
(
v
))}
:
clip_view
::
image_adaptor
{
imchvalue
<
value_type
>
(
other
.
base
()).
set_params
(
params
).
build
()}
,
m_subdomain
{
other
.
m_subdomain
}
{
}
...
...
pylene/include/mln/core/image/view/value_extended.hpp
View file @
25a92452
...
...
@@ -36,8 +36,10 @@ namespace mln
using
extension_type
=
extension
::
by_value
<
image_value_t
<
I
>>
;
using
value_type
=
image_value_t
<
I
>
;
using
reference
=
const
value_type
;
// Restrict the image to be read-only by copy, should not be const and be
// checked on pixel concept (but issue with proxy)
// FIXME: use common_reference here between image_reference_t<I> AND value_type&
using
reference
=
image_reference_t
<
I
>
;
// Not write only (we may want an out of bound value while keeping the
// the writability of the image)
using
category_type
=
std
::
common_type_t
<
image_category_t
<
I
>
,
bidirectional_image_tag
>
;
using
typename
image_adaptor
<
I
>::
domain_type
;
...
...
pylene/include/mln/labeling/experimental/local_extrema.hpp
0 → 100644
View file @
25a92452
#pragma once
#include
<mln/core/image/image.hpp>
#include
<mln/core/image/view/value_extended.hpp>
#include
<mln/core/neighborhood/neighborhood.hpp>
#include
<mln/core/trace.hpp>
#include
<mln/morpho/experimental/canvas/unionfind.hpp>
#include
<type_traits>
#include
<functional>
namespace
mln
::
labeling
::
experimental
{
/// Compute and labelize the local mimima of an image
///
/// \param[in] input Input image
/// \param[in] nbh neighborhood
/// \param[out] nlabel Number of minima
/// \param[in] cmp (optional) Strict weak ordering comparison function for values
template
<
class
Label_t
,
class
I
,
class
N
,
class
Compare
=
std
::
less
<
>
>
[[
gnu
::
noinline
]]
//
image_ch_value_t
<
std
::
remove_reference_t
<
I
>
,
Label_t
>
local_minima
(
I
&&
input
,
N
&&
nbh
,
int
&
nlabel
,
Compare
cmp
=
Compare
{});
/// Compute and labelize the local maxima of an image
///
/// \param[in] input Input image
/// \param[in] nbh neighborhood
/// \param[out] nlabel Number of maxima
template
<
class
Label_t
,
class
I
,
class
N
>
[[
gnu
::
noinline
]]
//
image_ch_value_t
<
std
::
remove_reference_t
<
I
>
,
Label_t
>
local_maxima
(
I
&&
input
,
N
&&
nbh
,
int
&
nlabel
);
/******************************************/
/**** Implementation ****/
/******************************************/
namespace
impl
{
// Output must initialized to Label_t(-1)
template
<
class
I
,
class
O
,
class
N
,
class
Compare
>
[[
gnu
::
noinline
]]
int
local_minima
(
I
input
,
N
nbh
,
O
output
,
Compare
cmp
)
{
using
Label_t
=
image_value_t
<
O
>
;
using
point_t
=
image_point_t
<
I
>
;
using
mln
::
morpho
::
experimental
::
canvas
::
impl
::
zfindroot
;
constexpr
Label_t
kUnseen
=
static_cast
<
Label_t
>
(
-
1
);
image_ch_value_t
<
I
,
point_t
>
parent
=
imchvalue
<
point_t
>
(
input
);
{
// Forward scan