29 template<sdt Dim = 1, sdt DimRes = 1,
class Real__ = Real, sdt BinCount = 100>
36 typedef typename Real_::DoubleType Double_;
46 typedef function<VecRes (const Vec&)>
Func;
59 Vegas(
const Func& func,
RandomGen& gen,
const Vec& lower,
const Vec& upper,
sdt sampleCount = 1000, Real warmUp = 0.1,
sdt iterCount = 5, Real alpha = 1.5) :
61 func(func), gen(gen), lower(lower), upper(upper), sampleCount(sampleCount), warmUp(Alge::max(warmUp,0)), iterCount(iterCount), alpha(alpha),
62 tgral(0), chi2a(0), sd(0), _progress(0), sampleTotal(0) {}
71 const VecRes&
integrate(Real progressDelta = 1);
76 const VecRes&
result()
const {
return tgral; }
78 const VecRes&
chiSqr()
const {
return chi2a; }
80 const VecRes&
stdDev()
const {
return sd; }
83 void init(
sdt init,
sdt sampleCount);
84 void rebin(Real rc,
sdt nd, Real r[], Real xin[], Real xi[]);
85 void integrate_priv(
sdt samplesMax);
135 Real d[BinCount][
dim];
136 Real di[BinCount][
dim];
138 Real xi[
dim][BinCount];
163 template<sdt Dim, sdt DimRes,
class Real, sdt BinCount>
164 const typename Vegas<Dim,DimRes,Real,BinCount>::VecRes&
167 sdt sampleWarmUp = warmUp*sampleCount;
171 if (sampleWarmUp > 0)
172 init(0, sampleWarmUp);
174 init(0, sampleCount);
177 _progress =
Alge::min(_progress + progressDelta, 1);
178 sdt sampleAcc = _progress*(sampleWarmUp+sampleCount) - sampleTotal;
179 sampleTotal += sampleAcc;
181 if (sampleTotal - sampleAcc < sampleWarmUp)
184 integrate_priv(sampleTotal < sampleWarmUp ? sampleAcc : -1);
185 if (sampleTotal < sampleWarmUp)
188 sampleAcc = sampleTotal - sampleWarmUp;
189 init(1, sampleCount);
193 integrate_priv(_progress < 1 ? sampleAcc : -1);
195 if (iterCur == iterCount)
202 template<sdt Dim, sdt DimRes,
class Real, sdt BinCount>
212 for (
sdt j=0; j<dim; ++j) xi[j][0] = 1;
217 for (
sdt j=0; j<dimRes; ++j)
234 if ((2*ng-BinCount) >= 0)
249 for (
sdt i=0; i<dim; ++i) k *= ng;
250 npg = sampleCount/k > 2 ? sampleCount/k : 2;
254 for (
sdt i=0; i<dim; ++i) dv2g *= dxg;
255 dv2g = calls*calls*dv2g*dv2g/npg/npg/(npg-1.0);
258 xJac = 1/
Real(calls);
259 for (
sdt j=0; j<dim; ++j)
261 dx[j] = upper[j]-lower[j];
266 for (
sdt i=0; i<(nd>ndo?nd:ndo); ++i) r[i] = 1;
267 for (
sdt j=0; j<dim; ++j) rebin(ndo/xnd,nd,r,xin,xi[j]);
273 template<sdt Dim, sdt DimRes,
class Real, sdt BinCount>
274 void Vegas<Dim,DimRes,Real,BinCount>::integrate_priv(
sdt samplesMax)
277 samplesMax *= iterCount;
279 for (; iterCur < iterCount; ++iterCur, ++ittot)
285 for (
sdt j=0; j<dimRes; ++j) Ab[j].ti = Ab[j].tsi = 0;
286 for (
sdt j=0; j<dim; ++j)
289 for (
sdt i=0; i<nd; ++i) d[i][j] = di[i][j] = 0;
298 for (
sdt j=0; j<dimRes; ++j)
305 for (
sdt k=npgCur; k<npg; ++k, ++samples)
307 if (samplesMax >= 0 && samples >= samplesMax)
315 for (
sdt j=0; j<dim; ++j)
318 Real xn = (kg[j]-xrand)*dxg+1;
319 ia[j] = (xn<BinCount) ? xn : BinCount;
320 ia[j] = (ia[j]>1) ? ia[j] : 1;
324 xo = xi[j][ia[j]-1]-xi[j][ia[j]-2];
325 rc = xi[j][ia[j]-2]+(xn-ia[j])*xo;
332 x[j] = lower[j]+rc*dx[j];
335 VecRes f = func(const_cast<const Vec&>(x));
336 for (
sdt j=0; j<dimRes; ++j)
338 if (f[j] != 0) ++Ax[j].npg;
340 Ax[j].f2 = f[j]*f[j];
342 Ax[j].f2b += Ax[j].f2;
344 for (
sdt j=0; j<dim; ++j)
346 di[ia[j]-1][j] += f[0];
347 if (mds >= 0) d[ia[j]-1][j] += Ax[0].f2;
352 for (
sdt j=0; j<dimRes; ++j)
355 Ax[j].f2b = (Ax[j].f2b-Ax[j].fb)*(Ax[j].f2b+Ax[j].fb);
356 if (Ax[j].f2b <= 0) Ax[j].f2b = Real_::smallest;
357 Ab[j].ti += Ax[j].fb;
358 Ab[j].tsi += Ax[j].f2b;
362 for (
sdt j=0; j<dim; ++j) d[ia[j]-1][j] += Ax[0].f2b;
365 for (k=dim-1; k>=0; --k)
368 if (++kg[k] != 1)
break;
374 for (
sdt j=0; j<dimRes; ++j)
377 Ai[j].Wgt = 1/Ab[j].tsi;
378 Ai[j].sInt += Ai[j].Wgt*Ab[j].ti;
379 Ai[j].sChi += Ai[j].Wgt*Ab[j].ti*Ab[j].ti;
380 Ai[j].sWgt += Ai[j].Wgt;
381 tgral[j] = Ai[j].sInt/Ai[j].sWgt;
382 chi2a[j] = (Ai[j].sChi-Ai[j].sInt*tgral[j])/(ittot-0.9999);
383 if (chi2a[j] < 0) chi2a[j] = 0;
389 for (
sdt j=0; j<dim; ++j)
395 for (
sdt i=1; i<nd-1; ++i)
403 d[nd-1][j] = (xo+xn)/2;
406 for (
sdt j=0; j<dim; ++j)
409 for (
sdt i=0; i<nd; ++i)
411 if (d[i][j] < Real_::smallest) d[i][j] = Real_::smallest;
416 rebin(rc/xnd,nd,r,xin,xi[j]);
421 template<sdt Dim, sdt DimRes,
class Real, sdt BinCount>
422 void Vegas<Dim, DimRes, Real, BinCount>::rebin(
Real rc,
sdt nd,
Real r[],
Real xin[],
Real xi[])
430 for (i=0; i<nd-1; i++)
434 if (k > 1) xo = xi[k-2];
437 xin[i] = xn-(xn-xo)*dr/r[k-1];
439 for (i=0; i<nd-1; i++) xi[i] = xin[i];
function< VecRes(const Vec &)> Func
Definition: Vegas.h:46
static Real pow(Real x, Real y)
x raised to exponent y
Definition: Alge.h:73
Algebra.
Definition: Alge.h:13
Random number generator interface.
Definition: Gen.h:11
~Vegas()
Definition: Vegas.h:64
ptrdiff_t sdt
Size difference type, shorthand for ptrdiff_t.
Definition: Core.h:92
Vec< dimRes, Real > VecRes
Definition: Vegas.h:44
static Real sqrt(Real x)
Square Root.
Definition: Alge.h:63
static std::common_type< Num, Num2 >::type min(Num a, Num2 b)
Get the minimum of two numbers.
Definition: Alge.h:89
Vegas(const Func &func, RandomGen &gen, const Vec &lower, const Vec &upper, sdt sampleCount=1000, Real warmUp=0.1, sdt iterCount=5, Real alpha=1.5)
Constructor, set up constants for all integration calls.
Definition: Vegas.h:59
const VecRes & stdDev() const
Estimate of standard deviation of integral result. Indicative of +- error range in result...
Definition: Vegas.h:80
Real progress() const
Current progress of calculation, from 0 (start) to 1 (complete).
Definition: Vegas.h:74
float Real
Real number type. See Real_ for real number operations and constants.
Definition: Real.h:21
Numeric type information, use numeral() to get instance safely from a static context.
Definition: Numeral.h:17
double Real
Definition: Real.h:14
Real__ Real
Definition: Vegas.h:33
const VecRes & result() const
Get current result of integration (same value returned by Integrate)
Definition: Vegas.h:76
const VecRes & integrate(Real progressDelta=1)
Perform integral calculation. The calculation can be split up over multiple calls.
Definition: Vegas.h:165
const VecRes & chiSqr() const
Get chi-square statistic for integral. A value that differs significantly from 1 (eg. diff > 0.5) indicates an unreliable result and more samples or iterations are required.
Definition: Vegas.h:78
static const sdt dimRes
Definition: Vegas.h:43
Vec< dim, Real > Vec
Definition: Vegas.h:45
static const sdt dim
Definition: Vegas.h:42
Monte Carlo (random-based) method to approximate the integral of a function over any number of dimens...
Definition: Vegas.h:30
Global Honeycomb namespace.
static Real log(Real x)
Natural logarithm. ie. ln(x)
Definition: Alge.h:80