37 #ifndef VIGRA_NOISE_NORMALIZATION_HXX
38 #define VIGRA_NOISE_NORMALIZATION_HXX
40 #include "utilities.hxx"
41 #include "tinyvector.hxx"
42 #include "stdimage.hxx"
43 #include "transformimage.hxx"
44 #include "combineimages.hxx"
45 #include "localminmax.hxx"
46 #include "functorexpression.hxx"
47 #include "numerictraits.hxx"
48 #include "separableconvolution.hxx"
49 #include "linear_solve.hxx"
50 #include "array_vector.hxx"
51 #include "static_assert.hxx"
96 noise_estimation_quantile(1.5),
97 averaging_quantile(0.8),
98 noise_variance_initial_guess(10.0),
119 vigra_precondition(r > 0,
120 "NoiseNormalizationOptions: window radius must be > 0.");
132 vigra_precondition(c > 0,
133 "NoiseNormalizationOptions: cluster count must be > 0.");
147 vigra_precondition(quantile > 0.0 && quantile <= 1.0,
148 "NoiseNormalizationOptions: averaging quantile must be between 0 and 1.");
149 averaging_quantile = quantile;
161 vigra_precondition(quantile > 0.0,
162 "NoiseNormalizationOptions: noise estimation quantile must be > 0.");
163 noise_estimation_quantile = quantile;
174 vigra_precondition(guess > 0.0,
175 "NoiseNormalizationOptions: noise variance initial guess must be > 0.");
176 noise_variance_initial_guess = guess;
180 unsigned int window_radius, cluster_count;
181 double noise_estimation_quantile, averaging_quantile, noise_variance_initial_guess;
187 template <
class ArgumentType,
class ResultType>
188 class NonparametricNoiseNormalizationFunctor
192 double lower, a, b, shift;
195 ArrayVector<Segment> segments_;
198 double exec(
unsigned int k, T t)
const
200 if(segments_[k].a == 0.0)
206 return 2.0 / segments_[k].a *
VIGRA_CSTD::sqrt(std::max(0.0, segments_[k].a * t + segments_[k].b));
211 typedef ArgumentType argument_type;
212 typedef ResultType result_type;
214 template <
class Vector>
215 NonparametricNoiseNormalizationFunctor(Vector
const & clusters)
216 : segments_(clusters.size()-1)
218 for(
unsigned int k = 0; k<segments_.size(); ++k)
220 segments_[k].lower = clusters[k][0];
221 segments_[k].a = (clusters[k+1][1] - clusters[k][1]) / (clusters[k+1][0] - clusters[k][0]);
222 segments_[k].b = clusters[k][1] - segments_[k].a * clusters[k][0];
229 segments_[k].shift = segments_[k].lower - exec(k, segments_[k].lower);
233 segments_[k].shift = exec(k-1, segments_[k].lower) - exec(k, segments_[k].lower) + segments_[k-1].shift;
238 result_type operator()(argument_type t)
const
242 for(; k < segments_.size(); ++k)
243 if(t < segments_[k].lower)
247 return detail::RequiresExplicitCast<ResultType>::cast(exec(k, t) + segments_[k].shift);
251 template <
class ArgumentType,
class ResultType>
252 class QuadraticNoiseNormalizationFunctor
254 double a, b, c, d, f, o;
256 void init(
double ia,
double ib,
double ic,
double xmin)
275 typedef ArgumentType argument_type;
276 typedef ResultType result_type;
278 template <
class Vector>
279 QuadraticNoiseNormalizationFunctor(Vector
const & clusters)
281 double xmin = NumericTraits<double>::max();
282 Matrix<double> m(3,3), r(3, 1), l(3, 1);
283 for(
unsigned int k = 0; k<clusters.size(); ++k)
286 l(1,0) = clusters[k][0];
287 l(2,0) =
sq(clusters[k][0]);
289 r += clusters[k][1]*l;
290 if(clusters[k][0] < xmin)
291 xmin = clusters[k][0];
295 init(l(0,0), l(1,0), l(2,0), xmin);
298 result_type operator()(argument_type t)
const
305 return detail::RequiresExplicitCast<ResultType>::cast(r);
309 template <
class ArgumentType,
class ResultType>
310 class LinearNoiseNormalizationFunctor
314 void init(
double ia,
double ib,
double xmin)
329 typedef ArgumentType argument_type;
330 typedef ResultType result_type;
332 template <
class Vector>
333 LinearNoiseNormalizationFunctor(Vector
const & clusters)
335 double xmin = NumericTraits<double>::max();
336 Matrix<double> m(2,2), r(2, 1), l(2, 1);
337 for(
unsigned int k = 0; k<clusters.size(); ++k)
340 l(1,0) = clusters[k][0];
342 r += clusters[k][1]*l;
343 if(clusters[k][0] < xmin)
344 xmin = clusters[k][0];
348 init(l(0,0), l(1,0), xmin);
351 result_type operator()(argument_type t)
const
358 return detail::RequiresExplicitCast<ResultType>::cast(r);
362 #define VIGRA_NoiseNormalizationFunctor(name, type, size) \
363 template <class ResultType> \
364 class name<type, ResultType> \
366 ResultType lut_[size]; \
369 typedef type argument_type; \
370 typedef ResultType result_type; \
372 template <class Vector> \
373 name(Vector const & clusters) \
375 name<double, ResultType> f(clusters); \
377 for(unsigned int k = 0; k < size; ++k) \
383 result_type operator()(argument_type t) const \
389 VIGRA_NoiseNormalizationFunctor(NonparametricNoiseNormalizationFunctor,
UInt8, 256)
390 VIGRA_NoiseNormalizationFunctor(NonparametricNoiseNormalizationFunctor,
UInt16, 65536)
391 VIGRA_NoiseNormalizationFunctor(QuadraticNoiseNormalizationFunctor,
UInt8, 256)
392 VIGRA_NoiseNormalizationFunctor(QuadraticNoiseNormalizationFunctor, UInt16, 65536)
393 VIGRA_NoiseNormalizationFunctor(LinearNoiseNormalizationFunctor, UInt8, 256)
394 VIGRA_NoiseNormalizationFunctor(LinearNoiseNormalizationFunctor, UInt16, 65536)
396 #undef VIGRA_NoiseNormalizationFunctor
400 template <
class SrcIterator,
class SrcAcessor,
403 iterativeNoiseEstimationChi2(SrcIterator s, SrcAcessor src, GradIterator g,
404 double & mean,
double & variance,
405 double robustnessThreshold,
int windowRadius)
407 double l2 =
sq(robustnessThreshold);
411 Diff2D ul(-windowRadius, -windowRadius);
412 int r2 =
sq(windowRadius);
414 for(
int iter=0; iter<100 ; ++iter)
419 unsigned int count = 0;
420 unsigned int tcount = 0;
422 SrcIterator siy = s + ul;
423 GradIterator giy = g + ul;
424 for(
int y=-windowRadius; y <= windowRadius; y++, ++siy.y, ++giy.y)
426 typename SrcIterator::row_iterator six = siy.rowIterator();
427 typename GradIterator::row_iterator gix = giy.rowIterator();
428 for(
int x=-windowRadius; x <= windowRadius; x++, ++six, ++gix)
430 if (
sq(x) +
sq(y) > r2)
434 if (*gix < l2*variance)
445 double oldvariance = variance;
446 variance= f * gsum / count;
450 return (count >= tcount * countThreshold / 2.0);
455 template <
class SrcIterator,
class SrcAcessor,
458 iterativeNoiseEstimationGauss(SrcIterator s, SrcAcessor src, GradIterator,
459 double & mean,
double & variance,
460 double robustnessThreshold,
int windowRadius)
462 double l2 =
sq(robustnessThreshold);
468 Diff2D ul(-windowRadius, -windowRadius);
469 int r2 =
sq(windowRadius);
471 for(
int iter=0; iter<100 ; ++iter)
476 unsigned int count = 0;
477 unsigned int tcount = 0;
479 SrcIterator siy = s + ul;
480 for(
int y=-windowRadius; y <= windowRadius; y++, ++siy.y)
482 typename SrcIterator::row_iterator six = siy.rowIterator();
483 for(
int x=-windowRadius; x <= windowRadius; x++, ++six)
485 if (
sq(x) +
sq(y) > r2)
489 if (
sq(src(six) - mean) < l2*variance)
492 sum2 +=
sq(src(six));
500 double oldmean = mean;
501 double oldvariance = variance;
503 variance= f * (sum2 / count -
sq(mean));
507 return (count >= tcount * countThreshold / 2.0);
513 template <
class SrcIterator,
class SrcAccessor,
514 class DestIterator,
class DestAccessor>
516 symmetricDifferenceSquaredMagnitude(
517 SrcIterator sul, SrcIterator slr, SrcAccessor src,
518 DestIterator dul, DestAccessor dest)
520 using namespace functor;
521 int w = slr.x - sul.x;
522 int h = slr.y - sul.y;
524 typedef typename NumericTraits<typename SrcAccessor::value_type>::RealPromote TmpType;
525 typedef BasicImage<TmpType> TmpImage;
527 Kernel1D<double> mask;
528 mask.initSymmetricGradient();
529 mask.setBorderTreatment(BORDER_TREATMENT_REFLECT);
531 TmpImage dx(w, h), dy(w, h);
534 combineTwoImages(srcImageRange(dx), srcImage(dy), destIter(dul, dest), Arg1()*Arg1() + Arg2()*Arg2());
537 template <
class SrcIterator,
class SrcAccessor,
538 class DestIterator,
class DestAccessor>
540 findHomogeneousRegionsFoerstner(
541 SrcIterator sul, SrcIterator slr, SrcAccessor src,
542 DestIterator dul, DestAccessor dest,
543 unsigned int windowRadius = 6,
double homogeneityThreshold = 40.0)
545 using namespace vigra::functor;
546 int w = slr.x - sul.x;
547 int h = slr.y - sul.y;
549 typedef typename NumericTraits<typename SrcAccessor::value_type>::RealPromote TmpType;
550 typedef BasicImage<TmpType> TmpImage;
554 ifThenElse(Arg1() <= Param(homogeneityThreshold), Param(1), Param(0)));
557 discErosion(srcImageRange(btmp), destIter(dul, dest), windowRadius);
560 template <
class SrcIterator,
class SrcAccessor,
561 class DestIterator,
class DestAccessor>
563 findHomogeneousRegions(
564 SrcIterator sul, SrcIterator slr, SrcAccessor src,
565 DestIterator dul, DestAccessor dest)
570 template <
class Vector1,
class Vector2>
571 void noiseVarianceListMedianCut(Vector1
const & noise, Vector2 & clusters,
572 unsigned int maxClusterCount)
574 typedef typename Vector2::value_type Result;
576 clusters.push_back(Result(0, noise.size()));
578 while(clusters.size() <= maxClusterCount)
581 unsigned int kMax = 0;
582 double diffMax = 0.0;
583 for(
unsigned int k=0; k < clusters.size(); ++k)
585 int k1 = clusters[k][0], k2 = clusters[k][1]-1;
587 #if 0 // turned the "internal error" in a postcondition message
589 std::string message(
"noiseVarianceListMedianCut(): internal error (");
590 message += std::string(
"k: ") +
asString(k) +
", ";
591 message += std::string(
"k1: ") +
asString(k1) +
", ";
592 message += std::string(
"k2: ") +
asString(k2) +
", ";
593 message += std::string(
"noise.size(): ") +
asString(noise.size()) +
", ";
594 message += std::string(
"clusters.size(): ") +
asString(clusters.size()) +
").";
595 vigra_invariant(k1 >= 0 && k1 < (
int)noise.size() && k2 >= 0 && k2 < (int)noise.size(), message.c_str());
598 vigra_postcondition(k1 >= 0 && k1 < (
int)noise.size() &&
599 k2 >= 0 && k2 < (int)noise.size(),
600 "noiseVarianceClustering(): Unable to find homogeneous regions.");
602 double diff = noise[k2][0] - noise[k1][0];
613 unsigned int k1 = clusters[kMax][0],
614 k2 = clusters[kMax][1];
615 unsigned int kSplit = k1 + (k2 - k1) / 2;
616 clusters[kMax][1] = kSplit;
617 clusters.push_back(Result(kSplit, k2));
621 struct SortNoiseByMean
624 bool operator()(T
const & l, T
const & r)
const
630 struct SortNoiseByVariance
633 bool operator()(T
const & l, T
const & r)
const
639 template <
class Vector1,
class Vector2,
class Vector3>
640 void noiseVarianceClusterAveraging(Vector1 & noise, Vector2 & clusters,
641 Vector3 & result,
double quantile)
643 typedef typename Vector1::iterator Iter;
644 typedef typename Vector3::value_type Result;
646 for(
unsigned int k=0; k<clusters.size(); ++k)
648 Iter i1 = noise.begin() + clusters[k][0];
649 Iter i2 = noise.begin() + clusters[k][1];
651 std::sort(i1, i2, SortNoiseByVariance());
653 std::size_t size =
static_cast<std::size_t
>(
VIGRA_CSTD::ceil(quantile*(i2 - i1)));
654 if(static_cast<std::size_t>(i2 - i1) < size)
665 variance += (*i1)[1];
668 result.push_back(Result(mean / size, variance / size));
672 template <
class SrcIterator,
class SrcAccessor,
class BackInsertable>
673 void noiseVarianceEstimationImpl(SrcIterator sul, SrcIterator slr, SrcAccessor src,
674 BackInsertable & result,
675 NoiseNormalizationOptions
const & options)
677 typedef typename BackInsertable::value_type ResultType;
679 unsigned int w = slr.x - sul.x;
680 unsigned int h = slr.y - sul.y;
682 typedef typename NumericTraits<typename SrcAccessor::value_type>::RealPromote TmpType;
683 typedef BasicImage<TmpType> TmpImage;
685 TmpImage gradient(w, h);
686 symmetricDifferenceSquaredMagnitude(sul, slr, src, gradient.upperLeft(), gradient.accessor());
689 findHomogeneousRegions(gradient.upperLeft(), gradient.lowerRight(), gradient.accessor(),
690 homogeneous.upperLeft(), homogeneous.accessor());
693 unsigned int windowRadius = options.window_radius;
694 for(
unsigned int y=windowRadius; y<h-windowRadius; ++y)
696 for(
unsigned int x=windowRadius; x<w-windowRadius; ++x)
698 if (! homogeneous(x, y))
702 double mean = 0.0, variance = options.noise_variance_initial_guess;
706 if(options.use_gradient)
708 success = iterativeNoiseEstimationChi2(sul + center, src,
709 gradient.upperLeft() + center, mean, variance,
710 options.noise_estimation_quantile, windowRadius);
714 success = iterativeNoiseEstimationGauss(sul + center, src,
715 gradient.upperLeft() + center, mean, variance,
716 options.noise_estimation_quantile, windowRadius);
720 result.push_back(ResultType(mean, variance));
726 template <
class Vector,
class BackInsertable>
727 void noiseVarianceClusteringImpl(Vector & noise, BackInsertable & result,
728 unsigned int clusterCount,
double quantile)
730 std::sort(noise.begin(), noise.end(), detail::SortNoiseByMean());
732 ArrayVector<TinyVector<unsigned int, 2> > clusters;
733 detail::noiseVarianceListMedianCut(noise, clusters, clusterCount);
735 std::sort(clusters.begin(), clusters.end(), detail::SortNoiseByMean());
737 detail::noiseVarianceClusterAveraging(noise, clusters, result, quantile);
740 template <
class Functor,
741 class SrcIterator,
class SrcAccessor,
742 class DestIterator,
class DestAccessor>
744 noiseNormalizationImpl(SrcIterator sul, SrcIterator slr, SrcAccessor src,
745 DestIterator dul, DestAccessor dest,
746 NoiseNormalizationOptions
const & options)
748 ArrayVector<TinyVector<double, 2> > noiseData;
749 noiseVarianceEstimationImpl(sul, slr, src, noiseData, options);
751 if(noiseData.size() < 10)
754 ArrayVector<TinyVector<double, 2> > noiseClusters;
756 noiseVarianceClusteringImpl(noiseData, noiseClusters,
757 options.cluster_count, options.averaging_quantile);
764 template <
class SrcIterator,
class SrcAccessor,
765 class DestIterator,
class DestAccessor>
767 nonparametricNoiseNormalizationImpl(SrcIterator sul, SrcIterator slr, SrcAccessor src,
768 DestIterator dul, DestAccessor dest,
769 NoiseNormalizationOptions
const & options,
772 typedef typename SrcAccessor::value_type SrcType;
773 typedef typename DestAccessor::value_type DestType;
774 return noiseNormalizationImpl<NonparametricNoiseNormalizationFunctor<SrcType, DestType> >
775 (sul, slr, src, dul, dest, options);
778 template <
class SrcIterator,
class SrcAccessor,
779 class DestIterator,
class DestAccessor>
781 nonparametricNoiseNormalizationImpl(SrcIterator sul, SrcIterator slr, SrcAccessor src,
782 DestIterator dul, DestAccessor dest,
783 NoiseNormalizationOptions
const & options,
786 int bands = src.size(sul);
787 for(
int b=0; b<bands; ++b)
789 VectorElementAccessor<SrcAccessor> sband(b, src);
790 VectorElementAccessor<DestAccessor> dband(b, dest);
791 typedef typename VectorElementAccessor<SrcAccessor>::value_type SrcType;
792 typedef typename VectorElementAccessor<DestAccessor>::value_type DestType;
794 if(!noiseNormalizationImpl<NonparametricNoiseNormalizationFunctor<SrcType, DestType> >
795 (sul, slr, sband, dul, dband, options))
801 template <
class SrcIterator,
class SrcAccessor,
802 class DestIterator,
class DestAccessor>
804 quadraticNoiseNormalizationImpl(SrcIterator sul, SrcIterator slr, SrcAccessor src,
805 DestIterator dul, DestAccessor dest,
806 NoiseNormalizationOptions
const & options,
809 typedef typename SrcAccessor::value_type SrcType;
810 typedef typename DestAccessor::value_type DestType;
811 return noiseNormalizationImpl<QuadraticNoiseNormalizationFunctor<SrcType, DestType> >
812 (sul, slr, src, dul, dest, options);
815 template <
class SrcIterator,
class SrcAccessor,
816 class DestIterator,
class DestAccessor>
818 quadraticNoiseNormalizationImpl(SrcIterator sul, SrcIterator slr, SrcAccessor src,
819 DestIterator dul, DestAccessor dest,
820 NoiseNormalizationOptions
const & options,
823 int bands = src.size(sul);
824 for(
int b=0; b<bands; ++b)
826 VectorElementAccessor<SrcAccessor> sband(b, src);
827 VectorElementAccessor<DestAccessor> dband(b, dest);
828 typedef typename VectorElementAccessor<SrcAccessor>::value_type SrcType;
829 typedef typename VectorElementAccessor<DestAccessor>::value_type DestType;
831 if(!noiseNormalizationImpl<QuadraticNoiseNormalizationFunctor<SrcType, DestType> >
832 (sul, slr, sband, dul, dband, options))
838 template <
class SrcIterator,
class SrcAccessor,
839 class DestIterator,
class DestAccessor>
841 quadraticNoiseNormalizationImpl(SrcIterator sul, SrcIterator slr, SrcAccessor src,
842 DestIterator dul, DestAccessor dest,
843 double a0,
double a1,
double a2,
846 ArrayVector<TinyVector<double, 2> > noiseClusters;
847 noiseClusters.push_back(TinyVector<double, 2>(0.0, a0));
848 noiseClusters.push_back(TinyVector<double, 2>(1.0, a0 + a1 + a2));
849 noiseClusters.push_back(TinyVector<double, 2>(2.0, a0 + 2.0*a1 + 4.0*a2));
851 QuadraticNoiseNormalizationFunctor<
typename SrcAccessor::value_type,
852 typename DestAccessor::value_type>(noiseClusters));
855 template <
class SrcIterator,
class SrcAccessor,
856 class DestIterator,
class DestAccessor>
858 quadraticNoiseNormalizationImpl(SrcIterator sul, SrcIterator slr, SrcAccessor src,
859 DestIterator dul, DestAccessor dest,
860 double a0,
double a1,
double a2,
863 int bands = src.size(sul);
864 for(
int b=0; b<bands; ++b)
866 VectorElementAccessor<SrcAccessor> sband(b, src);
867 VectorElementAccessor<DestAccessor> dband(b, dest);
868 quadraticNoiseNormalizationImpl(sul, slr, sband, dul, dband, a0, a1, a2, VigraTrueType());
872 template <
class SrcIterator,
class SrcAccessor,
873 class DestIterator,
class DestAccessor>
875 linearNoiseNormalizationImpl(SrcIterator sul, SrcIterator slr, SrcAccessor src,
876 DestIterator dul, DestAccessor dest,
877 NoiseNormalizationOptions
const & options,
880 typedef typename SrcAccessor::value_type SrcType;
881 typedef typename DestAccessor::value_type DestType;
882 return noiseNormalizationImpl<LinearNoiseNormalizationFunctor<SrcType, DestType> >
883 (sul, slr, src, dul, dest, options);
886 template <
class SrcIterator,
class SrcAccessor,
887 class DestIterator,
class DestAccessor>
889 linearNoiseNormalizationImpl(SrcIterator sul, SrcIterator slr, SrcAccessor src,
890 DestIterator dul, DestAccessor dest,
891 NoiseNormalizationOptions
const & options,
894 int bands = src.size(sul);
895 for(
int b=0; b<bands; ++b)
897 VectorElementAccessor<SrcAccessor> sband(b, src);
898 VectorElementAccessor<DestAccessor> dband(b, dest);
899 typedef typename VectorElementAccessor<SrcAccessor>::value_type SrcType;
900 typedef typename VectorElementAccessor<DestAccessor>::value_type DestType;
902 if(!noiseNormalizationImpl<LinearNoiseNormalizationFunctor<SrcType, DestType> >
903 (sul, slr, sband, dul, dband, options))
909 template <
class SrcIterator,
class SrcAccessor,
910 class DestIterator,
class DestAccessor>
912 linearNoiseNormalizationImpl(SrcIterator sul, SrcIterator slr, SrcAccessor src,
913 DestIterator dul, DestAccessor dest,
914 double a0,
double a1,
917 ArrayVector<TinyVector<double, 2> > noiseClusters;
918 noiseClusters.push_back(TinyVector<double, 2>(0.0, a0));
919 noiseClusters.push_back(TinyVector<double, 2>(1.0, a0 + a1));
921 LinearNoiseNormalizationFunctor<
typename SrcAccessor::value_type,
922 typename DestAccessor::value_type>(noiseClusters));
925 template <
class SrcIterator,
class SrcAccessor,
926 class DestIterator,
class DestAccessor>
928 linearNoiseNormalizationImpl(SrcIterator sul, SrcIterator slr, SrcAccessor src,
929 DestIterator dul, DestAccessor dest,
930 double a0,
double a1,
933 int bands = src.size(sul);
934 for(
int b=0; b<bands; ++b)
936 VectorElementAccessor<SrcAccessor> sband(b, src);
937 VectorElementAccessor<DestAccessor> dband(b, dest);
938 linearNoiseNormalizationImpl(sul, slr, sband, dul, dband, a0, a1, VigraTrueType());
945 struct noiseVarianceEstimation_can_only_work_on_scalar_images
946 : vigra::staticAssert::AssertBool<P>
1037 template <
class SrcIterator,
class SrcAccessor,
class BackInsertable>
1040 BackInsertable & result,
1041 NoiseNormalizationOptions
const & options = NoiseNormalizationOptions())
1043 typedef typename BackInsertable::value_type ResultType;
1044 typedef typename SrcAccessor::value_type SrcType;
1045 typedef typename NumericTraits<SrcType>::isScalar isScalar;
1047 VIGRA_STATIC_ASSERT((
1048 noiseVarianceEstimation_can_only_work_on_scalar_images<(isScalar::asBool)>));
1050 detail::noiseVarianceEstimationImpl(sul, slr, src, result, options);
1053 template <
class SrcIterator,
class SrcAccessor,
class BackInsertable>
1056 BackInsertable & result,
1057 NoiseNormalizationOptions
const & options = NoiseNormalizationOptions())
1126 template <
class SrcIterator,
class SrcAccessor,
class BackInsertable>
1129 BackInsertable & result,
1130 NoiseNormalizationOptions
const & options = NoiseNormalizationOptions())
1132 ArrayVector<TinyVector<double, 2> > variance;
1134 detail::noiseVarianceClusteringImpl(variance, result, options.cluster_count, options.averaging_quantile);
1137 template <
class SrcIterator,
class SrcAccessor,
class BackInsertable>
1140 BackInsertable & result,
1141 NoiseNormalizationOptions
const & options = NoiseNormalizationOptions())
1217 template <
class SrcIterator,
class SrcAccessor,
1218 class DestIterator,
class DestAccessor>
1221 DestIterator dul, DestAccessor dest,
1222 NoiseNormalizationOptions
const & options = NoiseNormalizationOptions())
1224 typedef typename SrcAccessor::value_type SrcType;
1226 return detail::nonparametricNoiseNormalizationImpl(sul, slr, src, dul, dest, options,
1227 typename NumericTraits<SrcType>::isScalar());
1230 template <
class SrcIterator,
class SrcAccessor,
1231 class DestIterator,
class DestAccessor>
1234 pair<DestIterator, DestAccessor> dest,
1235 NoiseNormalizationOptions
const & options = NoiseNormalizationOptions())
1297 template <
class SrcIterator,
class SrcAccessor,
1298 class DestIterator,
class DestAccessor>
1301 DestIterator dul, DestAccessor dest,
1302 NoiseNormalizationOptions
const & options = NoiseNormalizationOptions())
1304 typedef typename SrcAccessor::value_type SrcType;
1306 return detail::quadraticNoiseNormalizationImpl(sul, slr, src, dul, dest, options,
1307 typename NumericTraits<SrcType>::isScalar());
1310 template <
class SrcIterator,
class SrcAccessor,
1311 class DestIterator,
class DestAccessor>
1314 pair<DestIterator, DestAccessor> dest,
1315 NoiseNormalizationOptions
const & options = NoiseNormalizationOptions())
1381 template <
class SrcIterator,
class SrcAccessor,
1382 class DestIterator,
class DestAccessor>
1385 DestIterator dul, DestAccessor dest,
1386 double a0,
double a1,
double a2)
1388 typedef typename SrcAccessor::value_type SrcType;
1390 detail::quadraticNoiseNormalizationImpl(sul, slr, src, dul, dest, a0, a1, a2,
1391 typename NumericTraits<SrcType>::isScalar());
1394 template <
class SrcIterator,
class SrcAccessor,
1395 class DestIterator,
class DestAccessor>
1398 pair<DestIterator, DestAccessor> dest,
1399 double a0,
double a1,
double a2)
1461 template <
class SrcIterator,
class SrcAccessor,
1462 class DestIterator,
class DestAccessor>
1465 DestIterator dul, DestAccessor dest,
1466 NoiseNormalizationOptions
const & options = NoiseNormalizationOptions())
1468 typedef typename SrcAccessor::value_type SrcType;
1470 return detail::linearNoiseNormalizationImpl(sul, slr, src, dul, dest, options,
1471 typename NumericTraits<SrcType>::isScalar());
1474 template <
class SrcIterator,
class SrcAccessor,
1475 class DestIterator,
class DestAccessor>
1478 pair<DestIterator, DestAccessor> dest,
1479 NoiseNormalizationOptions
const & options = NoiseNormalizationOptions())
1545 template <
class SrcIterator,
class SrcAccessor,
1546 class DestIterator,
class DestAccessor>
1549 DestIterator dul, DestAccessor dest,
1550 double a0,
double a1)
1552 typedef typename SrcAccessor::value_type SrcType;
1554 detail::linearNoiseNormalizationImpl(sul, slr, src, dul, dest, a0, a1,
1555 typename NumericTraits<SrcType>::isScalar());
1558 template <
class SrcIterator,
class SrcAccessor,
1559 class DestIterator,
class DestAccessor>
1562 pair<DestIterator, DestAccessor> dest,
1563 double a0,
double a1)
1572 #endif // VIGRA_NOISE_NORMALIZATION_HXX