[ VIGRA Homepage | Function Index | Class Index | Namespaces | File List | Main Page ]

localminmax.hxx
1 /************************************************************************/
2 /* */
3 /* Copyright 1998-2002 by Ullrich Koethe */
4 /* */
5 /* This file is part of the VIGRA computer vision library. */
6 /* The VIGRA Website is */
7 /* http://hci.iwr.uni-heidelberg.de/vigra/ */
8 /* Please direct questions, bug reports, and contributions to */
9 /* ullrich.koethe@iwr.uni-heidelberg.de or */
10 /* vigra@informatik.uni-hamburg.de */
11 /* */
12 /* Permission is hereby granted, free of charge, to any person */
13 /* obtaining a copy of this software and associated documentation */
14 /* files (the "Software"), to deal in the Software without */
15 /* restriction, including without limitation the rights to use, */
16 /* copy, modify, merge, publish, distribute, sublicense, and/or */
17 /* sell copies of the Software, and to permit persons to whom the */
18 /* Software is furnished to do so, subject to the following */
19 /* conditions: */
20 /* */
21 /* The above copyright notice and this permission notice shall be */
22 /* included in all copies or substantial portions of the */
23 /* Software. */
24 /* */
25 /* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND */
26 /* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES */
27 /* OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND */
28 /* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT */
29 /* HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, */
30 /* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING */
31 /* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR */
32 /* OTHER DEALINGS IN THE SOFTWARE. */
33 /* */
34 /************************************************************************/
35 
36 
37 #ifndef VIGRA_LOCALMINMAX_HXX
38 #define VIGRA_LOCALMINMAX_HXX
39 
40 #include <vector>
41 #include <functional>
42 #include "utilities.hxx"
43 #include "stdimage.hxx"
44 #include "initimage.hxx"
45 #include "labelimage.hxx"
46 #include "pixelneighborhood.hxx"
47 
48 namespace vigra {
49 
50 /** \addtogroup LocalMinMax Local Minima and Maxima
51 
52  Detect local minima and maxima of the gray level,
53  including extremal plateaus larger than 1 pixel
54 */
55 //@{
56 
57 namespace detail {
58 
59 template <class SrcIterator, class SrcAccessor,
60  class DestIterator, class DestAccessor,
61  class DestValue, class Neighborhood,
62  class Compare>
63 void
64 localMinMax(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
65  DestIterator dul, DestAccessor da,
66  DestValue marker, Neighborhood,
67  Compare compare)
68 {
69  int w = slr.x - sul.x - 2;
70  int h = slr.y - sul.y - 2;
71 
72  int i,x,y;
73 
74  sul += Diff2D(1,1);
75  dul += Diff2D(1,1);
76 
77  for(y=0; y<h; ++y, ++sul.y, ++dul.y)
78  {
79  SrcIterator sx = sul;
80  DestIterator dx = dul;
81 
82  for(x=0; x<w; ++x, ++sx.x, ++dx.x)
83  {
84  typename SrcAccessor::value_type v = sa(sx);
85  NeighborhoodCirculator<SrcIterator, Neighborhood> sc(sx);
86  for(i = 0; i < Neighborhood::DirectionCount; ++i, ++sc)
87  {
88  if(!compare(v, sa(sc)))
89  break;
90  }
91 
92  if(i == Neighborhood::DirectionCount)
93  da.set(marker, dx);
94  }
95  }
96 }
97 
98 } // namespace detail
99 
100 
101 /********************************************************/
102 /* */
103 /* localMinima */
104 /* */
105 /********************************************************/
106 
107 /** \brief Find local minima in an image.
108 
109  The minima are found only when the have a size of one pixel.
110  Use \ref extendedLocalMinima() to find minimal plateaus. Minima are
111  marked in the destination image with the given marker value
112  (default is 1), all other destination pixels remain unchanged.
113  <TT>SrcAccessor::value_type</TT> must be less-comparable.
114  A pixel at the image border will never be marked as minimum.
115  Pass \ref vigra::EightNeighborCode or \ref vigra::FourNeighborCode
116  to determine the neighborhood where pixel values are compared.
117  The function uses accessors.
118 
119  <b> Declarations:</b>
120 
121  pass arguments explicitly:
122  \code
123  namespace vigra {
124  template <class SrcIterator, class SrcAccessor,
125  class DestIterator, class DestAccessor,
126  class DestValue = DestAccessor::value_type,
127  class Neighborhood = EightNeighborCode>
128  void
129  localMinima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
130  DestIterator dul, DestAccessor da,
131  DestValue marker = NumericTraits<DestValue>::one(),
132  Neighborhood neighborhood = EightNeighborCode())
133  }
134  \endcode
135 
136  use argument objects in conjunction with \ref ArgumentObjectFactories :
137  \code
138  namespace vigra {
139  template <class SrcIterator, class SrcAccessor,
140  class DestIterator, class DestAccessor,
141  class DestValue = DestAccessor::value_type,
142  class Neighborhood = EightNeighborCode>
143  void
144  localMinima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
145  pair<DestIterator, DestAccessor> dest,
146  DestValue marker = NumericTraits<DestValue>::one(),
147  Neighborhood neighborhood = EightNeighborCode())
148  }
149  \endcode
150 
151  <b> Usage:</b>
152 
153  <b>\#include</b> <<a href="localminmax_8hxx-source.html">vigra/localminmax.hxx</a>><br>
154  Namespace: vigra
155 
156  \code
157  vigra::BImage src(w,h), minima(w,h);
158 
159  // init destiniation image
160  minima = 0;
161 
162  vigra::localMinima(srcImageRange(src), destImage(minima));
163  \endcode
164 
165  <b> Required Interface:</b>
166 
167  \code
168  SrcImageIterator src_upperleft, src_lowerright;
169  DestImageIterator dest_upperleft;
170 
171  SrcAccessor src_accessor;
172  DestAccessor dest_accessor;
173 
174  SrcAccessor::value_type u = src_accessor(src_upperleft);
175 
176  u < u
177 
178  DestValue marker;
179  dest_accessor.set(marker, dest_upperleft);
180  \endcode
181 
182 */
183 doxygen_overloaded_function(template <...> void localMinima)
184 
185 template <class SrcIterator, class SrcAccessor,
186  class DestIterator, class DestAccessor,
187  class DestValue, class Neighborhood>
188 inline void
189 localMinima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
190  DestIterator dul, DestAccessor da,
191  DestValue marker, Neighborhood neighborhood)
192 {
193  detail::localMinMax(sul, slr, sa, dul, da, marker, neighborhood,
194  std::less<typename SrcAccessor::value_type>());
195 }
196 
197 template <class SrcIterator, class SrcAccessor,
198  class DestIterator, class DestAccessor, class DestValue>
199 inline void
200 localMinima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
201  DestIterator dul, DestAccessor da,
202  DestValue marker)
203 {
204  localMinima(sul, slr, sa, dul, da, marker, EightNeighborCode());
205 }
206 
207 template <class SrcIterator, class SrcAccessor,
208  class DestIterator, class DestAccessor>
209 inline void
210 localMinima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
211  DestIterator dul, DestAccessor da)
212 {
213  localMinima(sul, slr, sa, dul, da,
214  NumericTraits<typename DestAccessor::value_type>::one(),
216 }
217 
218 template <class SrcIterator, class SrcAccessor,
219  class DestIterator, class DestAccessor,
220  class DestValue, class Neighborhood>
221 inline void
222 localMinima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
223  pair<DestIterator, DestAccessor> dest,
224  DestValue marker, Neighborhood neighborhood)
225 {
226  localMinima(src.first, src.second, src.third,
227  dest.first, dest.second, marker, neighborhood);
228 }
229 
230 template <class SrcIterator, class SrcAccessor,
231  class DestIterator, class DestAccessor, class DestValue>
232 inline void
233 localMinima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
234  pair<DestIterator, DestAccessor> dest,
235  DestValue marker)
236 {
237  localMinima(src.first, src.second, src.third,
238  dest.first, dest.second, marker, EightNeighborCode());
239 }
240 
241 template <class SrcIterator, class SrcAccessor,
242  class DestIterator, class DestAccessor>
243 inline void
244 localMinima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
245  pair<DestIterator, DestAccessor> dest)
246 {
247  localMinima(src.first, src.second, src.third,
248  dest.first, dest.second,
249  NumericTraits<typename DestAccessor::value_type>::one(),
251 }
252 
253 /********************************************************/
254 /* */
255 /* localMaxima */
256 /* */
257 /********************************************************/
258 
259 /** \brief Find local maxima in an image.
260 
261  The maxima are found only when the have a size of one pixel.
262  Use \ref extendedLocalMaxima() to find maximal plateaus. Maxima are
263  marked in the destination image with the given marker value
264  (default is 1), all other destination pixels remain unchanged.
265  <TT>SrcAccessor::value_type</TT> must be less-comparable.
266  A pixel at the image border will never be marked as maximum.
267  The function uses accessors.
268 
269  <b> Declarations:</b>
270 
271  pass arguments explicitly:
272  \code
273  namespace vigra {
274  template <class SrcIterator, class SrcAccessor,
275  class DestIterator, class DestAccessor,
276  class DestValue = DestAccessor::value_type,
277  class Neighborhood = EightNeighborCode>
278  void
279  localMaxima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
280  DestIterator dul, DestAccessor da,
281  DestValue marker = NumericTraits<DestValue>::one(),
282  Neighborhood neighborhood = EightNeighborCode())
283  }
284  \endcode
285 
286  use argument objects in conjunction with \ref ArgumentObjectFactories :
287  \code
288  namespace vigra {
289  template <class SrcIterator, class SrcAccessor,
290  class DestIterator, class DestAccessor,
291  class DestValue = DestAccessor::value_type,
292  class Neighborhood = EightNeighborCode>
293  void
294  localMaxima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
295  pair<DestIterator, DestAccessor> dest,
296  DestValue marker = NumericTraits<DestValue>::one(),
297  Neighborhood neighborhood = EightNeighborCode())
298  }
299  \endcode
300 
301  <b> Usage:</b>
302 
303  <b>\#include</b> <<a href="localminmax_8hxx-source.html">vigra/localminmax.hxx</a>><br>
304  Namespace: vigra
305 
306  \code
307  vigra::BImage src(w,h), maxima(w,h);
308 
309  // init destiniation image
310  maxima = 0;
311 
312  vigra::localMaxima(srcImageRange(src), destImage(maxima));
313  \endcode
314 
315  <b> Required Interface:</b>
316 
317  \code
318  SrcImageIterator src_upperleft, src_lowerright;
319  DestImageIterator dest_upperleft;
320 
321  SrcAccessor src_accessor;
322  DestAccessor dest_accessor;
323 
324  SrcAccessor::value_type u = src_accessor(src_upperleft);
325 
326  u < u
327 
328  DestValue marker;
329  dest_accessor.set(marker, dest_upperleft);
330  \endcode
331 
332 */
333 doxygen_overloaded_function(template <...> void localMaxima)
334 
335 template <class SrcIterator, class SrcAccessor,
336  class DestIterator, class DestAccessor,
337  class DestValue, class Neighborhood>
338 inline void
339 localMaxima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
340  DestIterator dul, DestAccessor da,
341  DestValue marker, Neighborhood neighborhood)
342 {
343  detail::localMinMax(sul, slr, sa, dul, da, marker, neighborhood,
344  std::greater<typename SrcAccessor::value_type>());
345 }
346 
347 template <class SrcIterator, class SrcAccessor,
348  class DestIterator, class DestAccessor, class DestValue>
349 inline void
350 localMaxima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
351  DestIterator dul, DestAccessor da,
352  DestValue marker)
353 {
354  localMaxima(sul, slr, sa, dul, da, marker, EightNeighborCode());
355 }
356 
357 template <class SrcIterator, class SrcAccessor,
358  class DestIterator, class DestAccessor>
359 inline void
360 localMaxima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
361  DestIterator dul, DestAccessor da)
362 {
363  localMaxima(sul, slr, sa, dul, da,
364  NumericTraits<typename DestAccessor::value_type>::one(),
366 }
367 
368 template <class SrcIterator, class SrcAccessor,
369  class DestIterator, class DestAccessor,
370  class DestValue, class Neighborhood>
371 inline void
372 localMaxima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
373  pair<DestIterator, DestAccessor> dest,
374  DestValue marker, Neighborhood neighborhood)
375 {
376  localMaxima(src.first, src.second, src.third,
377  dest.first, dest.second, marker, neighborhood);
378 }
379 
380 template <class SrcIterator, class SrcAccessor,
381  class DestIterator, class DestAccessor, class DestValue>
382 inline void
383 localMaxima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
384  pair<DestIterator, DestAccessor> dest,
385  DestValue marker)
386 {
387  localMaxima(src.first, src.second, src.third,
388  dest.first, dest.second, marker, EightNeighborCode());
389 }
390 
391 template <class SrcIterator, class SrcAccessor,
392  class DestIterator, class DestAccessor>
393 inline void
394 localMaxima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
395  pair<DestIterator, DestAccessor> dest)
396 {
397  localMaxima(src.first, src.second, src.third,
398  dest.first, dest.second,
399  NumericTraits<typename DestAccessor::value_type>::one(),
401 }
402 
403 namespace detail {
404 
405 template <class SrcIterator, class SrcAccessor,
406  class DestIterator, class DestAccessor, class DestValue,
407  class Neighborhood, class Compare, class Equal>
408 void
409 extendedLocalMinMax(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
410  DestIterator dul, DestAccessor da, DestValue marker,
411  Neighborhood /*neighborhood*/, Compare compare, Equal equal)
412 {
413  typedef typename SrcAccessor::value_type SrcType;
414 
415  int w = slr.x - sul.x;
416  int h = slr.y - sul.y;
417 
418  int i,x,y;
419 
420  BasicImage<int> labels(w,h);
421 
422  int number_of_regions =
423  labelImage(sul, slr, sa, labels.upperLeft(), labels.accessor(),
424  (Neighborhood::DirectionCount == 8), equal);
425 
426  // assume that a region is a extremum until the opposite is proved
427  std::vector<unsigned char> isExtremum(number_of_regions+1, (unsigned char)1);
428 
429  BasicImage<int>::traverser ly = labels.upperLeft();
430 
431  for(y=0; y<h; ++y, ++sul.y, ++ly.y)
432  {
433  SrcIterator sx = sul;
434  BasicImage<int>::traverser lx(ly);
435 
436  for(x=0; x<w; ++x, ++sx.x, ++lx.x)
437  {
438  int lab = *lx;
439  if(x == 0 || y == 0 || x == w-1 || y == h-1)
440  {
441  // mark all regions that touch the image border as non-extremum
442  isExtremum[lab] = 0;
443  continue;
444  }
445 
446  SrcType v = sa(sx);
447  NeighborhoodCirculator<SrcIterator, Neighborhood> sc(sx);
448  NeighborhoodCirculator<BasicImage<int>::traverser, Neighborhood> lc(lx);
449  for(i=0; i<Neighborhood::DirectionCount; ++i, ++sc, ++lc)
450  {
451  if(lab != *lc && compare(sa(sc),v))
452  isExtremum[lab] = 0;
453  }
454 
455  }
456  }
457 
458  ly = labels.upperLeft();
459  for(y=0; y<h; ++y, ++dul.y, ++ly.y)
460  {
461  DestIterator xd = dul;
462  BasicImage<int>::Iterator lx(ly);
463 
464  for(x=0; x<w; ++x, ++xd.x, ++lx.x)
465  {
466  if(isExtremum[*lx])
467  da.set(marker, xd);
468  }
469  }
470 }
471 
472 } // namespace detail
473 
474 /********************************************************/
475 /* */
476 /* extendedLocalMinima */
477 /* */
478 /********************************************************/
479 
480 /** \brief Find local minimal regions in an image.
481 
482  This function finds regions of uniform pixel value
483  whose neighboring regions are all have smaller values
484  (minimal plateaus of arbitrary size). By default, the pixels
485  in a plateau have exactly identical values. By passing an <tt>EqualityFunctor</tt>
486  with tolerance, one can allow for plateaus that are not quite constant
487  (this is often necessary with float pixel values). Pass
488  \ref vigra::EightNeighborCode or \ref vigra::FourNeighborCode
489  to determine the neighborhood where pixel values are compared.
490 
491 
492  Minimal regions are
493  marked in the destination image with the given marker value
494  (default is 1), all other destination pixels remain unchanged.
495  <TT>SrcAccessor::value_type</TT> must be equality-comparable and
496  less-comparable.
497  A pixel or region touching the image border will never be marked as minimum or
498  minimal plateau.
499  The function uses accessors.
500 
501  <b> Declarations:</b>
502 
503  pass arguments explicitly:
504  \code
505  namespace vigra {
506  template <class SrcIterator, class SrcAccessor,
507  class DestIterator, class DestAccessor,
508  class DestValue = DestAccessor::value_type,
509  class Neighborhood = EightNeighborCode,
510  class EqualityFunctor = std::equal_to<typename SrcAssessor::value_type> >
511  void
512  extendedLocalMinima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
513  DestIterator dul, DestAccessor da,
514  DestValue marker = NumericTraits<DestValue>::one(),
515  Neighborhood neighborhood = EightNeighborCode(),
516  EqualityFunctor equal = EqualityFunctor())
517  }
518  \endcode
519 
520  use argument objects in conjunction with \ref ArgumentObjectFactories :
521  \code
522  namespace vigra {
523  template <class SrcIterator, class SrcAccessor,
524  class DestIterator, class DestAccessor,
525  class DestValue = DestAccessor::value_type,
526  class Neighborhood = EightNeighborCode,
527  class EqualityFunctor = std::equal_to<typename SrcAssessor::value_type> >
528  void
529  extendedLocalMinima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
530  pair<DestIterator, DestAccessor> dest,
531  DestValue marker = NumericTraits<DestValue>::one(),
532  Neighborhood neighborhood = EightNeighborCode(),
533  EqualityFunctor equal = EqualityFunctor())
534  }
535  \endcode
536 
537  <b> Usage:</b>
538 
539  <b>\#include</b> <<a href="localminmax_8hxx-source.html">vigra/localminmax.hxx</a>><br>
540  Namespace: vigra
541 
542  \code
543 
544  // optional: define an equality functor
545  template <class T>
546  struct EqualWithToleranceFunctor
547  {
548  EqualWithToleranceFunctor(T tolerance)
549  : t(tolerance)
550  {}
551 
552  bool operator()(T l, T r) const
553  {
554  return vigra::abs(l-r) <= t;
555  }
556 
557  T t;
558  };
559 
560  vigra::BImage src(w,h), minima(w,h);
561 
562  // init destiniation image
563  minima.init(0);
564 
565  vigra::extendedLocalMinima(srcImageRange(src), destImage(minima));
566 
567  // allow plateaus with tolerance
568  minima.init(0);
569  vigra::extendedLocalMinima(srcImageRange(src), destImage(minima), 1.0,
570  EqualWithToleranceFunctor<unsigned char>(1));
571  \endcode
572 
573  <b> Required Interface:</b>
574 
575  \code
576  SrcImageIterator src_upperleft, src_lowerright;
577  DestImageIterator dest_upperleft;
578 
579  SrcAccessor src_accessor;
580  DestAccessor dest_accessor;
581 
582  SrcAccessor::value_type u = src_accessor(src_upperleft);
583 
584  EqualityFunctor equal;
585  u == u
586  equal(u, u);
587  u < u
588 
589  DestValue marker;
590  dest_accessor.set(marker, dest_upperleft);
591  \endcode
592 
593 */
595 
596 template <class SrcIterator, class SrcAccessor,
597  class DestIterator, class DestAccessor, class DestValue,
598  class Neighborhood, class EqualityFunctor>
599 inline void
600 extendedLocalMinima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
601  DestIterator dul, DestAccessor da, DestValue marker,
602  Neighborhood neighborhood, EqualityFunctor equal)
603 {
604  typedef typename SrcAccessor::value_type SrcType;
605 
606  detail::extendedLocalMinMax(sul, slr, sa, dul, da,
607  marker, neighborhood,
608  std::less<SrcType>(), equal);
609 }
610 
611 template <class SrcIterator, class SrcAccessor,
612  class DestIterator, class DestAccessor, class DestValue,
613  class Neighborhood>
614 inline void
615 extendedLocalMinima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
616  DestIterator dul, DestAccessor da, DestValue marker,
617  Neighborhood neighborhood)
618 {
619  typedef typename SrcAccessor::value_type SrcType;
620 
621  extendedLocalMinima(sul, slr, sa, dul, da,
622  marker, neighborhood, std::equal_to<SrcType>());
623 }
624 
625 template <class SrcIterator, class SrcAccessor,
626  class DestIterator, class DestAccessor, class DestValue>
627 inline void
628 extendedLocalMinima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
629  DestIterator dul, DestAccessor da, DestValue marker)
630 {
631  typedef typename SrcAccessor::value_type SrcType;
632 
633  extendedLocalMinima(sul, slr, sa, dul, da,
634  marker, EightNeighborCode());
635 }
636 
637 template <class SrcIterator, class SrcAccessor,
638  class DestIterator, class DestAccessor>
639 inline void
640 extendedLocalMinima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
641  DestIterator dul, DestAccessor da)
642 {
643  extendedLocalMinima(sul, slr, sa, dul, da,
644  NumericTraits<typename DestAccessor::value_type>::one());
645 }
646 
647 template <class SrcIterator, class SrcAccessor,
648  class DestIterator, class DestAccessor, class DestValue,
649  class Neighborhood, class EqualityFunctor>
650 inline void
651 extendedLocalMinima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
652  pair<DestIterator, DestAccessor> dest,
653  DestValue marker, Neighborhood neighborhood,
654  EqualityFunctor equal)
655 {
656  extendedLocalMinima(src.first, src.second, src.third,
657  dest.first, dest.second, marker, neighborhood, equal);
658 }
659 
660 template <class SrcIterator, class SrcAccessor,
661  class DestIterator, class DestAccessor, class DestValue,
662  class Neighborhood>
663 inline void
664 extendedLocalMinima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
665  pair<DestIterator, DestAccessor> dest,
666  DestValue marker, Neighborhood neighborhood)
667 {
668  extendedLocalMinima(src.first, src.second, src.third,
669  dest.first, dest.second, marker, neighborhood);
670 }
671 
672 template <class SrcIterator, class SrcAccessor,
673  class DestIterator, class DestAccessor, class DestValue>
674 inline void
675 extendedLocalMinima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
676  pair<DestIterator, DestAccessor> dest,
677  DestValue marker)
678 {
679  extendedLocalMinima(src.first, src.second, src.third,
680  dest.first, dest.second, marker);
681 }
682 
683 template <class SrcIterator, class SrcAccessor,
684  class DestIterator, class DestAccessor>
685 inline void
686 extendedLocalMinima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
687  pair<DestIterator, DestAccessor> dest)
688 {
689  extendedLocalMinima(src.first, src.second, src.third,
690  dest.first, dest.second);
691 }
692 
693 /********************************************************/
694 /* */
695 /* extendedLocalMaxima */
696 /* */
697 /********************************************************/
698 
699 /** \brief Find local maximal regions in an image.
700 
701  This function finds regions of uniform pixel value
702  whose neighboring regions are all have smaller values
703  (maximal plateaus of arbitrary size). By default, the pixels
704  in a plateau have exactly identical values. By passing an <tt>EqualityFunctor</tt>
705  with tolerance, one can allow for plateaus that are not quite constant
706  (this is often necessary with float pixel values). Pass
707  \ref vigra::EightNeighborCode or \ref vigra::FourNeighborCode
708  to determine the neighborhood where pixel values are compared.
709 
710 
711  Maximal regions are
712  marked in the destination image with the given marker value
713  (default is 1), all other destination pixels remain unchanged.
714  <TT>SrcAccessor::value_type</TT> must be equality-comparable and
715  less-comparable.
716  A pixel or region touching the image border will never be marked as maximum or
717  maximal plateau.
718  The function uses accessors.
719 
720  <b> Declarations:</b>
721 
722  pass arguments explicitly:
723  \code
724  namespace vigra {
725  template <class SrcIterator, class SrcAccessor,
726  class DestIterator, class DestAccessor,
727  class DestValue = DestAccessor::value_type,
728  class Neighborhood = EightNeighborCode,
729  class EqualityFunctor = std::equal_to<typename SrcAssessor::value_type> >
730  void
731  extendedLocalMaxima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
732  DestIterator dul, DestAccessor da,
733  DestValue marker = NumericTraits<DestValue>::one(),
734  Neighborhood neighborhood = EightNeighborCode(),
735  EqualityFunctor equal = EqualityFunctor())
736  }
737  \endcode
738 
739  use argument objects in conjunction with \ref ArgumentObjectFactories :
740  \code
741  namespace vigra {
742  template <class SrcIterator, class SrcAccessor,
743  class DestIterator, class DestAccessor,
744  class DestValue = DestAccessor::value_type,
745  class Neighborhood = EightNeighborCode,
746  class EqualityFunctor = std::equal_to<typename SrcAssessor::value_type> >
747  void
748  extendedLocalMaxima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
749  pair<DestIterator, DestAccessor> dest,
750  DestValue marker = NumericTraits<DestValue>::one(),
751  Neighborhood neighborhood = EightNeighborCode(),
752  EqualityFunctor equal = EqualityFunctor())
753  }
754  \endcode
755 
756  <b> Usage:</b>
757 
758  <b>\#include</b> <<a href="localminmax_8hxx-source.html">vigra/localminmax.hxx</a>><br>
759  Namespace: vigra
760 
761  \code
762 
763  // optional: define an equality functor
764  template <class T>
765  struct EqualWithToleranceFunctor
766  {
767  EqualWithToleranceFunctor(T tolerance)
768  : t(tolerance)
769  {}
770 
771  bool operator()(T l, T r) const
772  {
773  return vigra::abs(l-r) <= t;
774  }
775 
776  T t;
777  };
778 
779  vigra::BImage src(w,h), maxima(w,h);
780 
781  // init destiniation image
782  maxima.init(0);
783 
784  vigra::extendedLocalMaxima(srcImageRange(src), destImage(maxima));
785 
786  // allow plateaus with tolerance
787  maxima.init(0);
788  vigra::extendedLocalMaxima(srcImageRange(src), destImage(maxima), 1.0,
789  EqualWithToleranceFunctor<unsigned char>(1));
790  \endcode
791 
792  <b> Required Interface:</b>
793 
794  \code
795  SrcImageIterator src_upperleft, src_lowerright;
796  DestImageIterator dest_upperleft;
797 
798  SrcAccessor src_accessor;
799  DestAccessor dest_accessor;
800 
801  SrcAccessor::value_type u = src_accessor(src_upperleft);
802 
803  EqualityFunctor equal;
804  u == u
805  equal(u, u);
806  u < u
807 
808  DestValue marker;
809  dest_accessor.set(marker, dest_upperleft);
810  \endcode
811 
812 */
814 
815 template <class SrcIterator, class SrcAccessor,
816  class DestIterator, class DestAccessor, class DestValue,
817  class Neighborhood, class EqualityFunctor>
818 inline void
819 extendedLocalMaxima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
820  DestIterator dul, DestAccessor da, DestValue marker,
821  Neighborhood neighborhood, EqualityFunctor equal)
822 {
823  typedef typename SrcAccessor::value_type SrcType;
824 
825  detail::extendedLocalMinMax(sul, slr, sa, dul, da,
826  marker, neighborhood,
827  std::greater<SrcType>(), equal);
828 }
829 
830 template <class SrcIterator, class SrcAccessor,
831  class DestIterator, class DestAccessor, class DestValue,
832  class Neighborhood>
833 inline void
834 extendedLocalMaxima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
835  DestIterator dul, DestAccessor da, DestValue marker,
836  Neighborhood neighborhood)
837 {
838  typedef typename SrcAccessor::value_type SrcType;
839 
840  extendedLocalMaxima(sul, slr, sa, dul, da,
841  marker, neighborhood, std::equal_to<SrcType>());
842 }
843 
844 template <class SrcIterator, class SrcAccessor,
845  class DestIterator, class DestAccessor, class DestValue>
846 inline void
847 extendedLocalMaxima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
848  DestIterator dul, DestAccessor da, DestValue marker)
849 {
850  typedef typename SrcAccessor::value_type SrcType;
851 
852  extendedLocalMaxima(sul, slr, sa, dul, da,
853  marker, EightNeighborCode());
854 }
855 
856 template <class SrcIterator, class SrcAccessor,
857  class DestIterator, class DestAccessor>
858 inline void
859 extendedLocalMaxima(SrcIterator sul, SrcIterator slr, SrcAccessor sa,
860  DestIterator dul, DestAccessor da)
861 {
862  extendedLocalMaxima(sul, slr, sa, dul, da,
863  NumericTraits<typename DestAccessor::value_type>::one());
864 }
865 
866 template <class SrcIterator, class SrcAccessor,
867  class DestIterator, class DestAccessor, class DestValue,
868  class Neighborhood, class EqualityFunctor>
869 inline void
870 extendedLocalMaxima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
871  pair<DestIterator, DestAccessor> dest,
872  DestValue marker, Neighborhood neighborhood,
873  EqualityFunctor equal)
874 {
875  extendedLocalMaxima(src.first, src.second, src.third,
876  dest.first, dest.second, marker, neighborhood, equal);
877 }
878 
879 template <class SrcIterator, class SrcAccessor,
880  class DestIterator, class DestAccessor, class DestValue,
881  class Neighborhood>
882 inline void
883 extendedLocalMaxima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
884  pair<DestIterator, DestAccessor> dest,
885  DestValue marker, Neighborhood neighborhood)
886 {
887  extendedLocalMaxima(src.first, src.second, src.third,
888  dest.first, dest.second, marker, neighborhood);
889 }
890 
891 template <class SrcIterator, class SrcAccessor,
892  class DestIterator, class DestAccessor, class DestValue>
893 inline void
894 extendedLocalMaxima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
895  pair<DestIterator, DestAccessor> dest,
896  DestValue marker)
897 {
898  extendedLocalMaxima(src.first, src.second, src.third,
899  dest.first, dest.second, marker);
900 }
901 
902 template <class SrcIterator, class SrcAccessor,
903  class DestIterator, class DestAccessor>
904 inline void
905 extendedLocalMaxima(triple<SrcIterator, SrcIterator, SrcAccessor> src,
906  pair<DestIterator, DestAccessor> dest)
907 {
908  extendedLocalMaxima(src.first, src.second, src.third,
909  dest.first, dest.second);
910 }
911 
912 //@}
913 
914 } // namespace vigra
915 
916 #endif // VIGRA_LOCALMINMAX_HXX

© Ullrich Köthe (ullrich.koethe@iwr.uni-heidelberg.de)
Heidelberg Collaboratory for Image Processing, University of Heidelberg, Germany

html generated using doxygen and Python
vigra 1.7.1 (Tue Jul 10 2012)