37 #ifndef VIGRA_INSPECTIMAGE_HXX
38 #define VIGRA_INSPECTIMAGE_HXX
42 #include "utilities.hxx"
43 #include "numerictraits.hxx"
44 #include "iteratortraits.hxx"
45 #include "functortraits.hxx"
46 #include "rgbvalue.hxx"
47 #include "inspector_passes.hxx"
63 template <
class SrcIterator,
class SrcAccessor,
class Functor>
65 inspectLine(SrcIterator s,
66 SrcIterator send, SrcAccessor src,
73 template <
class SrcIterator,
class SrcAccessor,
74 class MaskIterator,
class MaskAccessor,
77 inspectLineIf(SrcIterator s,
78 SrcIterator send, SrcAccessor src,
79 MaskIterator m, MaskAccessor mask,
82 for(; s != send; ++s, ++m)
87 template <
class SrcIterator1,
class SrcAccessor1,
88 class SrcIterator2,
class SrcAccessor2,
91 inspectTwoLines(SrcIterator1 s1,
92 SrcIterator1 s1end, SrcAccessor1 src1,
93 SrcIterator2 s2, SrcAccessor2 src2,
96 for(; s1 != s1end; ++s1, ++s2)
97 f(src1(s1), src2(s2));
100 template <
class SrcIterator1,
class SrcAccessor1,
101 class SrcIterator2,
class SrcAccessor2,
102 class MaskIterator,
class MaskAccessor,
105 inspectTwoLinesIf(SrcIterator1 s1,
106 SrcIterator1 s1end, SrcAccessor1 src1,
107 SrcIterator2 s2, SrcAccessor2 src2,
108 MaskIterator m, MaskAccessor mask,
111 for(; s1 != s1end; ++s1, ++s2, ++m)
113 f(src1(s1), src2(s2));
181 doxygen_overloaded_function(template <...>
void inspectImage)
183 template <
class ImageIterator,
class Accessor>
184 struct inspectImage_binder
186 ImageIterator upperleft;
187 ImageIterator lowerright;
190 inspectImage_binder(ImageIterator ul, ImageIterator lr, Accessor ac)
191 : upperleft(ul), lowerright(lr), a(ac) {}
192 template <
class Functor>
193 void operator()(Functor & f)
195 int w = lowerright.x - upperleft.x;
197 for (ImageIterator t = upperleft; t.y < lowerright.y; ++t.y)
199 inspectLine(t.rowIterator(), t.rowIterator() + w, a, f);
204 template <
class ImageIterator,
class Accessor,
class Functor>
206 inspectImage(ImageIterator upperleft, ImageIterator lowerright,
207 Accessor a, Functor & f)
209 inspectImage_binder<ImageIterator, Accessor> g(upperleft, lowerright, a);
210 detail::extra_passes_select(g, f);
213 template <
class ImageIterator,
class Accessor,
class Functor>
216 inspectImage(triple<ImageIterator, ImageIterator, Accessor> img,
224 template <
class T>
class UnaryAnalyser;
227 template <
class ImageIterator,
class Accessor,
class Functor>
230 inspectImage(ImageIterator upperleft, ImageIterator lowerright,
231 Accessor a, functor::UnaryAnalyser<Functor>
const & f)
234 const_cast<functor::UnaryAnalyser<Functor> &
>(f));
237 template <
class ImageIterator,
class Accessor,
class Functor>
240 inspectImage(triple<ImageIterator, ImageIterator, Accessor> img,
241 functor::UnaryAnalyser<Functor>
const & f)
244 const_cast<functor::UnaryAnalyser<Functor> &>(f));
327 template <
class ImageIterator,
class Accessor,
328 class MaskImageIterator,
class MaskAccessor>
329 struct inspectImageIf_binder
331 ImageIterator upperleft;
332 ImageIterator lowerright;
334 MaskImageIterator mask_upperleft;
337 inspectImageIf_binder(ImageIterator ul, ImageIterator lr, Accessor ac,
338 MaskImageIterator m_ul, MaskAccessor m_ac)
339 : upperleft(ul), lowerright(lr), a(ac), mask_upperleft(m_ul), ma(m_ac)
341 template <
class Functor>
342 void operator()(Functor & f)
344 int w = lowerright.x - upperleft.x;
346 MaskImageIterator mt = mask_upperleft;
347 for (ImageIterator t = upperleft; t.y < lowerright.y; ++t.y, ++mt.y)
349 inspectLineIf(t.rowIterator(),
350 t.rowIterator() + w, a,
351 mt.rowIterator(), ma, f);
356 template <
class ImageIterator,
class Accessor,
357 class MaskImageIterator,
class MaskAccessor,
class Functor>
360 ImageIterator lowerright, Accessor a,
361 MaskImageIterator mask_upperleft, MaskAccessor ma,
364 inspectImageIf_binder<ImageIterator, Accessor, MaskImageIterator,
366 g(upperleft, lowerright, a, mask_upperleft, ma);
367 detail::extra_passes_select(g, f);
370 template <
class ImageIterator,
class Accessor,
371 class MaskImageIterator,
class MaskAccessor,
class Functor>
374 inspectImageIf(triple<ImageIterator, ImageIterator, Accessor> img,
375 pair<MaskImageIterator, MaskAccessor> mask,
379 mask.first, mask.second, f);
382 template <
class ImageIterator,
class Accessor,
383 class MaskImageIterator,
class MaskAccessor,
class Functor>
386 ImageIterator lowerright, Accessor a,
387 MaskImageIterator mask_upperleft, MaskAccessor ma,
388 functor::UnaryAnalyser<Functor>
const & f)
391 mask_upperleft, ma,
const_cast<functor::UnaryAnalyser<Functor> &
>(f));
394 template <
class ImageIterator,
class Accessor,
395 class MaskImageIterator,
class MaskAccessor,
class Functor>
397 inspectImageIf(triple<ImageIterator, ImageIterator, Accessor> img,
398 pair<MaskImageIterator, MaskAccessor> mask,
399 functor::UnaryAnalyser<Functor>
const & f)
402 mask.first, mask.second, const_cast<functor::UnaryAnalyser<Functor> &>(f));
483 template <
class ImageIterator1,
class Accessor1,
484 class ImageIterator2,
class Accessor2>
485 struct inspectTwoImages_binder
487 ImageIterator1 upperleft1;
488 ImageIterator1 lowerright1;
490 ImageIterator2 upperleft2;
492 inspectTwoImages_binder(ImageIterator1 u1, ImageIterator1 l1, Accessor1 a1_,
493 ImageIterator2 u2, Accessor2 a2_)
494 : upperleft1(u1), lowerright1(l1), a1(a1_), upperleft2(u2), a2(a2_) {}
495 template <
class Functor>
496 void operator()(Functor & f)
498 int w = lowerright1.x - upperleft1.x;
500 ImageIterator1 t1 = upperleft1;
501 ImageIterator2 t2 = upperleft2;
502 for (; t1.y < lowerright1.y; ++t1.y, ++t2.y)
504 inspectTwoLines(t1.rowIterator(),
505 t1.rowIterator() + w, a1,
506 t2.rowIterator(), a2, f);
511 template <
class ImageIterator1,
class Accessor1,
512 class ImageIterator2,
class Accessor2,
517 ImageIterator2 upperleft2, Accessor2 a2,
520 inspectTwoImages_binder<ImageIterator1, Accessor1,
521 ImageIterator2, Accessor2>
522 g(upperleft1, lowerright1, a1, upperleft2, a2);
523 detail::extra_passes_select(g, f);
526 template <
class ImageIterator1,
class Accessor1,
527 class ImageIterator2,
class Accessor2,
532 pair<ImageIterator2, Accessor2> img2,
536 img2.first, img2.second, f);
539 template <
class ImageIterator1,
class Accessor1,
540 class ImageIterator2,
class Accessor2,
543 inspectTwoImages(ImageIterator1 upperleft1, ImageIterator1 lowerright1, Accessor1 a1,
544 ImageIterator2 upperleft2, Accessor2 a2,
545 functor::UnaryAnalyser<Functor>
const & f)
548 upperleft2, a2,
const_cast<functor::UnaryAnalyser<Functor> &
>(f));
551 template <
class ImageIterator1,
class Accessor1,
552 class ImageIterator2,
class Accessor2,
557 pair<ImageIterator2, Accessor2> img2,
558 functor::UnaryAnalyser<Functor>
const & f)
561 img2.first, img2.second, const_cast<functor::UnaryAnalyser<Functor> &>(f));
651 template <
class ImageIterator1,
class Accessor1,
652 class ImageIterator2,
class Accessor2,
653 class MaskImageIterator,
class MaskAccessor>
654 struct inspectTwoImagesIf_binder
656 ImageIterator1 upperleft1;
657 ImageIterator1 lowerright1;
659 ImageIterator2 upperleft2;
661 MaskImageIterator mupperleft;
663 inspectTwoImagesIf_binder(ImageIterator1 u1, ImageIterator1 l1,
664 Accessor1 a1_, ImageIterator2 u2, Accessor2 a2_,
665 MaskImageIterator mu, MaskAccessor ma)
666 : upperleft1(u1), lowerright1(l1), a1(a1_), upperleft2(u2), a2(a2_),
667 mupperleft(mu), mask(ma) {}
668 template <
class Functor>
669 void operator()(Functor & f)
671 int w = lowerright1.x - upperleft1.x;
673 ImageIterator1 t1 = upperleft1;
674 ImageIterator2 t2 = upperleft2;
675 MaskImageIterator mu = mupperleft;
676 for(; t1.y < lowerright1.y; ++t1.y, ++t2.y, ++mu.y)
678 inspectTwoLinesIf(t1.rowIterator(),
679 t1.rowIterator() + w, a1,
680 t2.rowIterator(), a2,
681 mu.rowIterator(), mask, f);
686 template <
class ImageIterator1,
class Accessor1,
687 class ImageIterator2,
class Accessor2,
688 class MaskImageIterator,
class MaskAccessor,
693 ImageIterator2 upperleft2, Accessor2 a2,
694 MaskImageIterator mupperleft, MaskAccessor mask,
697 inspectTwoImagesIf_binder<ImageIterator1, Accessor1,
698 ImageIterator2, Accessor2,
699 MaskImageIterator, MaskAccessor>
700 g(upperleft1, lowerright1, a1, upperleft2, a2, mupperleft, mask);
701 detail::extra_passes_select(g, f);
704 template <
class ImageIterator1,
class Accessor1,
705 class ImageIterator2,
class Accessor2,
706 class MaskImageIterator,
class MaskAccessor,
711 pair<ImageIterator2, Accessor2> img2,
712 pair<MaskImageIterator, MaskAccessor> m,
716 img2.first, img2.second,
721 template <
class ImageIterator1,
class Accessor1,
722 class ImageIterator2,
class Accessor2,
723 class MaskImageIterator,
class MaskAccessor,
726 inspectTwoImagesIf(ImageIterator1 upperleft1, ImageIterator1 lowerright1, Accessor1 a1,
727 ImageIterator2 upperleft2, Accessor2 a2,
728 MaskImageIterator mupperleft, MaskAccessor mask,
729 functor::UnaryAnalyser<Functor>
const & f)
734 const_cast<functor::UnaryAnalyser<Functor> &
>(f));
737 template <
class ImageIterator1,
class Accessor1,
738 class ImageIterator2,
class Accessor2,
739 class MaskImageIterator,
class MaskAccessor,
744 pair<ImageIterator2, Accessor2> img2,
745 pair<MaskImageIterator, MaskAccessor> m,
746 functor::UnaryAnalyser<Functor>
const & f)
749 img2.first, img2.second,
751 const_cast<functor::UnaryAnalyser<Functor> &>(f));
804 template <
class VALUETYPE>
896 template <
class VALUETYPE>
898 :
public FunctorTraitsBase<FindMinMax<VALUETYPE> >
901 typedef VigraTrueType isUnaryAnalyser;
946 template <
class VALUETYPE>
948 :
public UnaryReduceFunctorTag
970 sum_ = NumericTraits<result_type>::zero();
1051 template <
class VALUETYPE>
1074 typedef typename NumericTraits<VALUETYPE>::RealPromote
value_type;
1079 : sum_(NumericTraits<
result_type>::zero()), count_(0)
1087 sum_ = NumericTraits<result_type>::zero();
1128 return sum_ / (double)count_;
1135 return sum_ / (double)count_;
1142 template <
class VALUETYPE>
1143 class FunctorTraits<FindAverage<VALUETYPE> >
1144 :
public FunctorTraitsBase<FindAverage<VALUETYPE> >
1147 typedef VigraTrueType isInitializer;
1148 typedef VigraTrueType isUnaryAnalyser;
1204 template <
class VALUETYPE>
1227 typedef typename NumericTraits<VALUETYPE>::RealPromote
value_type;
1233 sumOfSquaredDifferences_(NumericTraits<
result_type>::zero()),
1242 mean_ = NumericTraits<result_type>::zero();
1243 sumOfSquaredDifferences_ = NumericTraits<result_type>::zero();
1254 sumOfSquaredDifferences_ += (count_-1.0)*t1*t2;
1272 sumOfSquaredDifferences_ +=
1273 (t1 * t1 * weight / count_) * (count_ - weight );
1280 double newCount = count_ + v.count_;
1281 sumOfSquaredDifferences_ += v.sumOfSquaredDifferences_ +
1282 count_ / newCount * v.count_ * (mean_ - v.mean_) * (mean_ - v.mean_);
1283 mean_ = (count_ * mean_ + v.count_ * v.mean_) / newCount;
1291 return (
unsigned int)count_;
1308 ? sumOfSquaredDifferences_ / (count_ - 1.0)
1309 : sumOfSquaredDifferences_ / count_;
1323 template <
class VALUETYPE>
1324 class FunctorTraits<FindAverageAndVariance<VALUETYPE> >
1325 :
public FunctorTraitsBase<FindAverageAndVariance<VALUETYPE> >
1328 typedef VigraTrueType isInitializer;
1329 typedef VigraTrueType isUnaryAnalyser;
1366 template <
class VALUETYPE>
1430 template <
class VALUETYPE>
1432 :
public FunctorTraitsBase<FindROISize<VALUETYPE> >
1435 typedef VigraTrueType isInitializer;
1436 typedef VigraTrueType isUnaryAnalyser;
1553 else if(otherRegion.
valid)
1580 class FunctorTraits<FindBoundingRectangle>
1581 :
public FunctorTraitsBase<FindBoundingRectangle>
1584 typedef VigraTrueType isInitializer;
1585 typedef VigraTrueType isUnaryAnalyser;
1624 template <
class VALUETYPE>
1669 template <
class VALUETYPE>
1671 :
public FunctorTraitsBase<LastValueFunctor<VALUETYPE> >
1674 typedef VigraTrueType isInitializer;
1675 typedef VigraTrueType isUnaryAnalyser;
1728 template <
class FUNCTOR,
class VALUETYPE>
1732 VALUETYPE start_, accumulator_;
1766 accumulator_(initial)
1772 { accumulator_ = start_; }
1781 accumulator_ = f_(accumulator_, v);
1788 template <
class T1,
class T2>
1791 accumulator_ = f_(accumulator_, v1, v2);
1797 {
return accumulator_; }
1800 template <
class FUNCTOR,
class VALUETYPE>
1801 ReduceFunctor<FUNCTOR, VALUETYPE>
1802 reduceFunctor(FUNCTOR
const & f, VALUETYPE
const & initial)
1804 return ReduceFunctor<FUNCTOR, VALUETYPE>(f, initial);
1807 template <
class FUNCTOR,
class VALUETYPE>
1808 class FunctorTraits<ReduceFunctor<FUNCTOR, VALUETYPE> >
1809 :
public FunctorTraitsBase<ReduceFunctor<FUNCTOR, VALUETYPE> >
1812 typedef VigraTrueType isInitializer;
1813 typedef VigraTrueType isUnaryAnalyser;
1814 typedef VigraTrueType isBinaryAnalyser;
1880 template <
class RegionStatistics,
class LabelType =
int>
1882 :
public detail::get_extra_passes<RegionStatistics>
1884 typedef std::vector<RegionStatistics> RegionArray;
1937 : regions(max_region_label+1)
1945 RegionArray newRegions(max_region_label+1);
1946 regions.swap(newRegions);
1953 RegionArray newRegions(regions.size());
1954 regions.swap(newRegions);
1961 regions[
static_cast<unsigned int>(label)](v);
1967 regions[
static_cast<unsigned int>(label1)](regions[static_cast<unsigned int>(label2)]);
1973 {
return size() - 1; }
1978 {
return regions.size(); }
1984 {
return regions[
static_cast<unsigned int>(label)](); }
1989 {
return regions[
static_cast<unsigned int>(label)]; }
1994 {
return regions[
static_cast<unsigned int>(label)]; }
1999 {
return regions.begin(); }
2004 {
return regions.begin(); }
2009 {
return regions.end(); }
2014 {
return regions.end(); }
2024 struct pass_n_dispatch
2027 unsigned pass_number;
2029 : x(a), pass_number(n) {}
2033 x.regions[
static_cast<unsigned>(label)].updatePassN(v, pass_number);
2037 pass_n_dispatch pass_n(N n)
2039 if (n < 2 || static_cast<unsigned>(n) > this->max_passes)
2040 vigra_fail(
"ArrayOfRegionStatistics::pass_n(): inconsistent use.");
2041 return pass_n_dispatch(*
this, n);
2044 std::vector<RegionStatistics> regions;
2047 template <
class RegionStatistics,
class LabelType>
2048 class FunctorTraits<ArrayOfRegionStatistics<RegionStatistics, LabelType> >
2049 :
public FunctorTraitsBase<ArrayOfRegionStatistics<RegionStatistics, LabelType> >
2052 typedef VigraTrueType isUnaryFunctor;
2053 typedef VigraTrueType isBinaryAnalyser;
2060 #endif // VIGRA_INSPECTIMAGE_HXX