69 RooGamma::RooGamma(
const char *name,
const char *title,
70 RooAbsReal& _x, RooAbsReal& _gamma,
71 RooAbsReal& _beta, RooAbsReal& _mu) :
72 RooAbsPdf(name,title),
73 x(
"x",
"Observable",this,_x),
74 gamma(
"gamma",
"Mean",this,_gamma),
75 beta(
"beta",
"Width",this,_beta),
76 mu(
"mu",
"Para",this,_mu)
78 RooHelpers::checkRangeOfParameters(
this, {&_gamma, &_beta}, 0.);
83 RooGamma::RooGamma(
const RooGamma& other,
const char* name) :
84 RooAbsPdf(other,name), x(
"x",this,other.x), gamma(
"mean",this,other.gamma),
85 beta(
"beta",this,other.beta), mu(
"mu",this,other.mu)
91 Double_t RooGamma::evaluate()
const
93 return TMath::GammaDist(x, gamma, mu, beta) ;
101 template<
class Tx,
class Tgamma,
class Tbeta,
class Tmu>
102 void compute(
size_t batchSize,
103 double * __restrict output,
104 Tx X, Tgamma G, Tbeta B, Tmu M)
106 constexpr
double NaN = std::numeric_limits<double>::quiet_NaN();
107 for (
size_t i=0; i<batchSize; i++) {
108 if (X[i]<M[i] || G[i] <= 0.0 || B[i] <= 0.0) {
112 output[i] = (G[i]==1.0)/B[i];
120 for (
size_t i=0; i<batchSize; i++) {
121 if (output[i] == 0.0) {
122 output[i] = -std::lgamma(G[i]);
127 double gamma = -std::lgamma(G[2019]);
128 for (
size_t i=0; i<batchSize; i++) {
129 if (output[i] == 0.0) {
135 for (
size_t i=0; i<batchSize; i++) {
137 const double invBeta = 1/B[i];
138 double arg = (X[i]-M[i])*invBeta;
140 arg = _rf_fast_log(arg);
141 output[i] += arg*(G[i]-1);
142 output[i] = _rf_fast_exp(output[i]);
143 output[i] *= invBeta;
149 RooSpan<double> RooGamma::evaluateBatch(std::size_t begin, std::size_t batchSize)
const {
150 using namespace BatchHelpers;
152 EvaluateInfo info = getInfo( {&x, &gamma, &beta, &mu}, begin, batchSize );
153 if (info.nBatches == 0) {
156 auto output = _batchData.makeWritableBatchUnInit(begin, batchSize);
157 auto xData = x.getValBatch(begin, info.size);
159 if (info.nBatches==1 && !xData.empty()) {
160 compute(info.size, output.data(), xData.data(),
161 BracketAdapter<double> (gamma),
162 BracketAdapter<double> (beta),
163 BracketAdapter<double> (mu));
166 compute(info.size, output.data(),
167 BracketAdapterWithMask (x,x.getValBatch(begin,info.size)),
168 BracketAdapterWithMask (gamma,gamma.getValBatch(begin,info.size)),
169 BracketAdapterWithMask (beta,beta.getValBatch(begin,info.size)),
170 BracketAdapterWithMask (mu,mu.getValBatch(begin,info.size)));
177 Int_t RooGamma::getAnalyticalIntegral(RooArgSet& allVars, RooArgSet& analVars,
const char* )
const
179 if (matchArgs(allVars,analVars,x))
return 1 ;
185 Double_t RooGamma::analyticalIntegral(Int_t code,
const char* rangeName)
const
190 Double_t integral = ROOT::Math::gamma_cdf(x.max(rangeName), gamma, beta, mu) - ROOT::Math::gamma_cdf(x.min(rangeName), gamma, beta, mu);
196 Int_t RooGamma::getGenerator(
const RooArgSet& directVars, RooArgSet &generateVars, Bool_t )
const
198 if (matchArgs(directVars,generateVars,x))
return 1 ;
211 void RooGamma::generateEvent(Int_t code)
223 d = gamma -1./3.; c = 1./TMath::Sqrt(9.*d);
226 xgen = RooRandom::randomGenerator()->Gaus(); v = 1. + c*xgen;
228 v = v*v*v; u = RooRandom::randomGenerator()->Uniform();
229 if( u < 1.-.0331*(xgen*xgen)*(xgen*xgen) ) {
230 if ( (((d*v)* beta + mu ) < x.max()) && (((d*v)* beta + mu) > x.min()) ) {
231 x = ((d*v)* beta + mu) ;
235 if( TMath::Log(u) < 0.5*xgen*xgen + d*(1.-v + TMath::Log(v)) ) {
236 if ( (((d*v)* beta + mu ) < x.max()) && (((d*v)* beta + mu) > x.min()) ) {
237 x = ((d*v)* beta + mu) ;