GammaLib  2.1.0.dev
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
GModelSpectralPlawEnergyFlux.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  * GModelSpectralPlawEnergyFlux.cpp - Spectral power law model class *
3  * ----------------------------------------------------------------------- *
4  * copyright (C) 2016-2021 by Michael Mayer *
5  * ----------------------------------------------------------------------- *
6  * *
7  * This program is free software: you can redistribute it and/or modify *
8  * it under the terms of the GNU General Public License as published by *
9  * the Free Software Foundation, either version 3 of the License, or *
10  * (at your option) any later version. *
11  * *
12  * This program is distributed in the hope that it will be useful, *
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of *
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
15  * GNU General Public License for more details. *
16  * *
17  * You should have received a copy of the GNU General Public License *
18  * along with this program. If not, see <http://www.gnu.org/licenses/>. *
19  * *
20  ***************************************************************************/
21 /**
22  * @file GModelSpectralPlawEnergyFlux.cpp
23  * @brief Energy flux normalized power law spectral model class implementation
24  * @author Michael Mayer
25  */
26 
27 /* __ Includes ___________________________________________________________ */
28 #ifdef HAVE_CONFIG_H
29 #include <config.h>
30 #endif
31 #include <cmath>
32 #include "GException.hpp"
33 #include "GTools.hpp"
34 #include "GMath.hpp"
35 #include "GRan.hpp"
38 
39 /* __ Constants __________________________________________________________ */
40 
41 /* __ Globals ____________________________________________________________ */
43  "EnergyFlux",
44  "Index",
45  "LowerLimit",
46  "UpperLimit");
47 const GModelSpectralRegistry g_spectral_plaw_eflux_registry(&g_spectral_plaw_eflux_seed);
48 
49 /* __ Method name definitions ____________________________________________ */
50 #define G_FLUX "GModelSpectralPlawEnergyFlux::flux(GEnergy&, GEnergy&)"
51 #define G_EFLUX "GModelSpectralPlawEnergyFlux::eflux(GEnergy&, GEnergy&)"
52 #define G_MC "GModelSpectralPlawEnergyFlux::mc(GEnergy&, GEnergy&, GTime&, "\
53  "GRan&)"
54 #define G_READ "GModelSpectralPlawEnergyFlux::read(GXmlElement&)"
55 #define G_WRITE "GModelSpectralPlawEnergyFlux::write(GXmlElement&)"
56 
57 /* __ Macros _____________________________________________________________ */
58 
59 /* __ Coding definitions _________________________________________________ */
60 
61 /* __ Debug definitions __________________________________________________ */
62 
63 
64 /*==========================================================================
65  = =
66  = Constructors/destructors =
67  = =
68  ==========================================================================*/
69 
70 /***********************************************************************//**
71  * @brief Void constructor
72  ***************************************************************************/
75 {
76  // Initialise members
77  init_members();
78 
79  // Return
80  return;
81 }
82 
83 
84 /***********************************************************************//**
85  * @brief Model type and parameter name constructor
86  *
87  * @param[in] type Model type.
88  * @param[in] eflux Name of energy flux parameter.
89  * @param[in] index Name of index parameter.
90  * @param[in] emin Name of emin parameter.
91  * @param[in] emax Name of emax parameter.
92  ***************************************************************************/
94  const std::string& eflux,
95  const std::string& index,
96  const std::string& emin,
97  const std::string& emax) :
99 {
100  // Initialise members
101  init_members();
102 
103  // Set model type
104  m_type = type;
105 
106  // Set parameter names
107  m_eflux.name(eflux);
108  m_index.name(index);
109  m_emin.name(emin);
110  m_emax.name(emax);
111 
112  // Return
113  return;
114 }
115 
116 
117 /***********************************************************************//**
118  * @brief Constructor
119  *
120  * @param[in] eflux Energy flux (erg/cm2/s).
121  * @param[in] index Power law index.
122  * @param[in] emin Minimum energy.
123  * @param[in] emax Maximum energy.
124  *
125  * Construct a spectral power law from the
126  * - energy flux (in erg/cm2/s),
127  * - spectral index,
128  * - minimum energy and
129  * - maximum energy.
130  ***************************************************************************/
132  const double& index,
133  const GEnergy& emin,
134  const GEnergy& emax) :
136 {
137  // Initialise members
138  init_members();
139 
140  // Set parameters
141  m_eflux.value(eflux);
142  m_index.value(index);
143  m_emin.value(emin.MeV());
144  m_emax.value(emax.MeV());
145 
146  // Return
147  return;
148 }
149 
150 
151 /***********************************************************************//**
152  * @brief XML constructor
153  *
154  * @param[in] xml XML element.
155  *
156  * Constructs energy flux normalized power law spectral model by extracting
157  * information from an XML element.
158  ***************************************************************************/
161 {
162  // Initialise members
163  init_members();
164 
165  // Read information from XML element
166  read(xml);
167 
168  // Return
169  return;
170 }
171 
172 
173 /***********************************************************************//**
174  * @brief Copy constructor
175  *
176  * @param[in] model Spectral power law model.
177  ***************************************************************************/
179  GModelSpectral(model)
180 {
181  // Initialise members
182  init_members();
183 
184  // Copy members
185  copy_members(model);
186 
187  // Return
188  return;
189 }
190 
191 
192 /***********************************************************************//**
193  * @brief Destructor
194  ***************************************************************************/
196 {
197  // Free members
198  free_members();
199 
200  // Return
201  return;
202 }
203 
204 
205 /*==========================================================================
206  = =
207  = Operators =
208  = =
209  ==========================================================================*/
210 
211 /***********************************************************************//**
212  * @brief Assignment operator
213  *
214  * @param[in] model Spectral power law model.
215  * @return Spectral power law model.
216  ***************************************************************************/
218 {
219  // Execute only if object is not identical
220  if (this != &model) {
221 
222  // Copy base class members
223  this->GModelSpectral::operator=(model);
224 
225  // Free members
226  free_members();
227 
228  // Initialise members
229  init_members();
230 
231  // Copy members
232  copy_members(model);
233 
234  } // endif: object was not identical
235 
236  // Return
237  return *this;
238 }
239 
240 
241 /*==========================================================================
242  = =
243  = Public methods =
244  = =
245  ==========================================================================*/
246 
247 /***********************************************************************//**
248  * @brief Clear power law model
249  ***************************************************************************/
251 {
252  // Free class members (base and derived classes, derived class first)
253  free_members();
255 
256  // Initialise members
258  init_members();
259 
260  // Return
261  return;
262 }
263 
264 
265 /***********************************************************************//**
266  * @brief Clone power law model
267  *
268  * @return Pointer to deep copy of power law model
269  ***************************************************************************/
271 {
272  // Clone power law model
273  return new GModelSpectralPlawEnergyFlux(*this);
274 }
275 
276 
277 /***********************************************************************//**
278  * @brief Evaluate function
279  *
280  * @param[in] srcEng True photon energy.
281  * @param[in] srcTime True photon arrival time.
282  * @param[in] gradients Compute gradients?
283  * @return Model value (ph/cm2/s/MeV).
284  *
285  * Computes
286  *
287  * \f[
288  * S_{\rm E}(E | t) = {\tt m\_eflux}
289  * \frac{{\tt m\_index}+2}
290  * {{\tt e\_max}^{{\tt m\_index}+2} -
291  * {\tt e\_min}^{{\tt m\_index}+2}}
292  * E^{\tt m\_index}
293  * \f]
294  *
295  * for \f${\tt m\_index} \ne -2\f$ and
296  *
297  * \f[
298  * S_{\rm E}(E | t) =
299  * \frac{{\tt m\_eflux}}
300  * {\log {\tt e\_max} - \log {\tt e\_min}}
301  * E^{\tt m\_index}
302  * \f]
303  *
304  * for \f${\tt m\_index} = -2\f$, where
305  * - \f${\tt e\_min}\f$ is the minimum energy of an interval,
306  * - \f${\tt e\_max}\f$ is the maximum energy of an interval,
307  * - \f${\tt m\_eflux}\f$ is the energy flux between
308  * \f${\tt e\_min}\f$ and \f${\tt e\_max}\f$, and
309  * - \f${\tt m\_index}\f$ is the spectral index.
310  *
311  * If the @p gradients flag is true the method will also compute the
312  * partial derivatives of the model with respect to the parameters using
313  *
314  * \f[
315  * \frac{\delta S_{\rm E}(E | t)}{\delta {\tt m\_eflux}} =
316  * \frac{S_{\rm E}(E | t)}{{\tt m\_eflux}}
317  * \f]
318  *
319  * \f[
320  * \frac{\delta S_{\rm E}(E | t)}{\delta {\tt m\_index}} =
321  * S_{\rm E}(E | t) \,
322  * \left( \frac{1}{{\tt m\_index}+2} -
323  * \frac{\log({\tt e\_max}) {\tt e\_max}^{{\tt m\_index}+2} -
324  * \log({\tt e\_min}) {\tt e\_min}^{{\tt m\_index}+2}}
325  * {{\tt e\_max}^{{\tt m\_index}+2} -
326  * {\tt e\_min}^{{\tt m\_index}+2}}
327  * + \ln(E) \right)
328  * \f]
329  *
330  * for \f${\tt m\_index} \ne -2\f$ and
331  *
332  * \f[
333  * \frac{\delta S_{\rm E}(E | t)}{\delta {\tt m\_index}} =
334  * S_{\rm E}(E | t) \, \ln(E)
335  * \f]
336  *
337  * for \f${\tt m\_index} = -2\f$.
338  *
339  * No partial derivatives are supported for the energy boundaries.
340  ***************************************************************************/
342  const GTime& srcTime,
343  const bool& gradients) const
344 {
345  // Update precomputed values
346  update(srcEng);
347 
348  // Compute function value
349  double value = m_eflux.value() * gammalib::erg2MeV * m_norm * m_power;
350 
351  // Optionally compute gradients
352  if (gradients) {
353 
354  // Compute partial derivatives of the parameter values
355  double g_eflux = (m_eflux.is_free() && m_eflux.factor_value() != 0.0)
356  ? g_eflux = value / m_eflux.factor_value()
357  : 0.0;
358  double g_index = (m_index.is_free())
359  ? value * (m_g_norm + gammalib::ln10 *
360  srcEng.log10MeV()) * m_index.scale()
361  : 0.0;
362 
363  // Set gradients
364  m_eflux.factor_gradient(g_eflux);
365  m_index.factor_gradient(g_index);
366 
367  } // endif: gradient computation was requested
368 
369  // Compile option: Check for NaN/Inf
370  #if defined(G_NAN_CHECK)
371  if (gammalib::is_notanumber(value) || gammalib::is_infinite(value)) {
372  std::cout << "*** ERROR: GModelSpectralPlawEnergyFlux::eval";
373  std::cout << "(srcEng=" << srcEng;
374  std::cout << ", srcTime=" << srcTime << "):";
375  std::cout << " NaN/Inf encountered";
376  std::cout << " (value=" << value;
377  std::cout << ", eflux=" << eflux();
378  std::cout << ", m_norm=" << m_norm;
379  std::cout << ", m_power=" << m_power;
380  std::cout << ")" << std::endl;
381  }
382  #endif
383 
384  // Return
385  return value;
386 }
387 
388 
389 /***********************************************************************//**
390  * @brief Returns model photon flux between [emin, emax] (units: ph/cm2/s)
391  *
392  * @param[in] emin Minimum photon energy.
393  * @param[in] emax Minimum photon energy.
394  * @return Photon flux (ph/cm2/s).
395  *
396  * Computes
397  *
398  * \f[
399  * \int_{\tt emin}^{\tt emax} S_{\rm E}(E | t) dE
400  * \f]
401  *
402  * where
403  * - [@p emin, @p emax] is an energy interval, and
404  * - \f$S_{\rm E}(E | t)\f$ is the spectral model (ph/cm2/s/MeV).
405  ***************************************************************************/
407  const GEnergy& emax) const
408 {
409  // Initialise flux
410  double flux = 0.0;
411 
412  // Compute only if integration range is valid
413  if (emin < emax) {
414 
415  // Compute power law normalization
416  double norm = 0.0;
417  if (index() != -2.0) {
418  double gamma = m_index.value() + 2.0;
419  double pow_ref_emin = std::pow(this->emin().MeV(), gamma);
420  double pow_ref_emax = std::pow(this->emax().MeV(), gamma);
421  norm = m_eflux.value() * gammalib::erg2MeV * gamma /
422  (pow_ref_emax - pow_ref_emin);
423  }
424  else {
425  double log_ref_emin = std::log(this->emin().MeV());
426  double log_ref_emax = std::log(this->emax().MeV());
427  norm = m_eflux.value() * gammalib::erg2MeV /
428  (log_ref_emax - log_ref_emin);
429  }
430 
431  // Compute photon flux
432  if (index() != -1.0) {
433  double gamma = m_index.value() + 1.0;
434  double pow_emin = std::pow(emin.MeV(), gamma);
435  double pow_emax = std::pow(emax.MeV(), gamma);
436  flux = norm / gamma * (pow_emax - pow_emin);
437  }
438 
439  // Case B: Index is -1
440  else {
441  double log_emin = std::log(emin.MeV());
442  double log_emax = std::log(emax.MeV());
443  flux = norm * (log_emax - log_emin);
444  }
445 
446  } // endif: integration range was valid
447 
448  // Return flux
449  return flux;
450 }
451 
452 
453 /***********************************************************************//**
454  * @brief Returns model energy flux between [emin, emax] (units: erg/cm2/s)
455  *
456  * @param[in] emin Minimum photon energy.
457  * @param[in] emax Minimum photon energy.
458  * @return Energy flux (erg/cm2/s).
459  *
460  * Computes
461  *
462  * \f[
463  * \int_{\tt emin}^{\tt emax} S_{\rm E}(E | t) E \, dE
464  * \f]
465  *
466  * where
467  * - [@p emin, @p emax] is an energy interval, and
468  * - \f$S_{\rm E}(E | t)\f$ is the spectral model (ph/cm2/s/MeV).
469  ***************************************************************************/
471  const GEnergy& emax) const
472 {
473  // Initialise flux
474  double eflux = 0.0;
475 
476  // Compute only if integration range is valid
477  if (emin < emax) {
478 
479  // Compute power law normalization
480  if (index() != -2.0) {
481  double gamma = m_index.value() + 2.0;
482  double pow_ref_emin = std::pow(this->emin().MeV(), gamma);
483  double pow_ref_emax = std::pow(this->emax().MeV(), gamma);
484  double pow_emin = std::pow(emin.MeV(), gamma);
485  double pow_emax = std::pow(emax.MeV(), gamma);
486  double factor = (pow_emax - pow_emin) /
487  (pow_ref_emax - pow_ref_emin);
488  eflux = m_eflux.value() * factor;
489  }
490  else {
491  double log_emin = std::log(emin.MeV());
492  double log_emax = std::log(emax.MeV());
493  double log_ref_emin = std::log(this->emin().MeV());
494  double log_ref_emax = std::log(this->emax().MeV());
495  double factor = (log_emax - log_emin) /
496  (log_ref_emax - log_ref_emin);
497  eflux = m_eflux.value() * factor;
498  }
499 
500  } // endif: integration range was valid
501 
502  // Return flux
503  return eflux;
504 }
505 
506 
507 /***********************************************************************//**
508  * @brief Returns MC energy between [emin, emax]
509  *
510  * @param[in] emin Minimum photon energy.
511  * @param[in] emax Maximum photon energy.
512  * @param[in] time True photon arrival time.
513  * @param[in,out] ran Random number generator.
514  * @return Energy.
515  *
516  * Returns Monte Carlo energy by randomly drawing from a power law.
517  ***************************************************************************/
519  const GEnergy& emax,
520  const GTime& time,
521  GRan& ran) const
522 {
523  // Check energy interval
525 
526  // Allocate energy
527  GEnergy energy;
528 
529  // Case A: Index is not -1
530  if (index() != -1.0) {
531  double exponent = index() + 1.0;
532  double e_max = std::pow(emax.MeV(), exponent);
533  double e_min = std::pow(emin.MeV(), exponent);
534  double u = ran.uniform();
535  double eng = (u > 0.0)
536  ? std::exp(std::log(u * (e_max - e_min) + e_min) / exponent)
537  : 0.0;
538  energy.MeV(eng);
539  }
540 
541  // Case B: Index is -1
542  else {
543  double e_max = std::log(emax.MeV());
544  double e_min = std::log(emin.MeV());
545  double u = ran.uniform();
546  double eng = std::exp(u * (e_max - e_min) + e_min);
547  energy.MeV(eng);
548  }
549 
550  // Return energy
551  return energy;
552 }
553 
554 
555 /***********************************************************************//**
556  * @brief Read model from XML element
557  *
558  * @param[in] xml XML element.
559  *
560  * Reads the spectral information from an XML element.
561  ***************************************************************************/
563 {
564  // Verify number of model parameters
566 
567  // Get parameter pointers
572 
573  // Read parameters
574  m_eflux.read(*eflux);
575  m_index.read(*index);
576  m_emin.read(*emin);
577  m_emax.read(*emax);
578 
579  // Return
580  return;
581 }
582 
583 
584 /***********************************************************************//**
585  * @brief Write model into XML element
586  *
587  * @param[in] xml XML element.
588  *
589  * Writes the spectral information into an XML element.
590  ***************************************************************************/
592 {
593  // Verify model type
595 
596  // Get XML parameters
601 
602  // Write parameters
603  m_eflux.write(*eflux);
604  m_index.write(*index);
605  m_emin.write(*emin);
606  m_emax.write(*emax);
607 
608  // Return
609  return;
610 }
611 
612 
613 /***********************************************************************//**
614  * @brief Print power law information
615  *
616  * @param[in] chatter Chattiness.
617  * @return String containing power law information.
618  ***************************************************************************/
619 std::string GModelSpectralPlawEnergyFlux::print(const GChatter& chatter) const
620 {
621  // Initialise result string
622  std::string result;
623 
624  // Continue only if chatter is not silent
625  if (chatter != SILENT) {
626 
627  // Append header
628  result.append("=== GModelSpectralPlawEnergyFlux ===");
629 
630  // Append information
631  result.append("\n"+gammalib::parformat("Number of parameters"));
632  result.append(gammalib::str(size()));
633  for (int i = 0; i < size(); ++i) {
634  result.append("\n"+m_pars[i]->print(chatter));
635  }
636 
637  } // endif: chatter was not silent
638 
639  // Return result
640  return result;
641 }
642 
643 
644 /*==========================================================================
645  = =
646  = Private methods =
647  = =
648  ==========================================================================*/
649 
650 /***********************************************************************//**
651  * @brief Initialise class members
652  ***************************************************************************/
654 {
655  // Initialise model type
656  m_type = "PowerLaw";
657 
658  // Initialise energy flux
659  m_eflux.clear();
660  m_eflux.name("EnergyFlux");
661  m_eflux.unit("erg/cm2/s");
662  m_eflux.scale(1.0);
663  m_eflux.value(1.0); // default: 1.0
664  m_eflux.range(0.0, 10.0); // range: [0,10]
665  m_eflux.free();
666  m_eflux.gradient(0.0);
667  m_eflux.has_grad(true);
668 
669  // Initialise powerlaw index
670  m_index.clear();
671  m_index.name("Index");
672  m_index.scale(1.0);
673  m_index.value(-2.0); // default: -2.0
674  m_index.range(-10.0,+10.0); // range: [-10,+10]
675  m_index.free();
676  m_index.gradient(0.0);
677  m_index.has_grad(true);
678 
679  // Initialise lower limit
680  m_emin.clear();
681  m_emin.name("LowerLimit");
682  m_emin.unit("MeV");
683  m_emin.scale(1.0);
684  m_emin.value(100.0); // default: 100
685  m_emin.range(0.001, 1.0e15); // range: [0.001, 1e15]
686  m_emin.fix();
687  m_emin.gradient(0.0);
688  m_emin.has_grad(false);
689 
690  // Initialise upper limit
691  m_emax.clear();
692  m_emax.name("UpperLimit");
693  m_emax.unit("MeV");
694  m_emax.scale(1.0);
695  m_emax.value(500000.0); // default: 500000
696  m_emin.range(0.001, 1.0e15); // range: [0.001, 1e15]
697  m_emax.fix();
698  m_emax.gradient(0.0);
699  m_emax.has_grad(false);
700 
701  // Set parameter pointer(s)
702  m_pars.clear();
703  m_pars.push_back(&m_eflux);
704  m_pars.push_back(&m_index);
705  m_pars.push_back(&m_emin);
706  m_pars.push_back(&m_emax);
707 
708  // Initialise last parameters (for fast computation)
709  m_log_emin = 0.0;
710  m_log_emax = 0.0;
711  m_pow_emin = 0.0;
712  m_pow_emax = 0.0;
713  m_norm = 0.0;
714  m_power = 0.0;
715  m_last_index = 1000.0;
716  m_last_emin.MeV(0.0);
717  m_last_emax.MeV(0.0);
718  m_last_energy.MeV(0.0);
719 
720  // Return
721  return;
722 }
723 
724 
725 /***********************************************************************//**
726  * @brief Copy class members
727  *
728  * @param[in] model Spectral power law model.
729  ***************************************************************************/
731 {
732  // Copy members
733  m_type = model.m_type;
734  m_eflux = model.m_eflux;
735  m_index = model.m_index;
736  m_emin = model.m_emin;
737  m_emax = model.m_emax;
738 
739  // Set parameter pointer(s)
740  m_pars.clear();
741  m_pars.push_back(&m_eflux);
742  m_pars.push_back(&m_index);
743  m_pars.push_back(&m_emin);
744  m_pars.push_back(&m_emax);
745 
746  // Copy bookkeeping information
747  m_log_emin = model.m_log_emin;
748  m_log_emax = model.m_log_emax;
749  m_pow_emin = model.m_pow_emin;
750  m_pow_emax = model.m_pow_emax;
751  m_norm = model.m_norm;
752  m_power = model.m_power;
753  m_last_index = model.m_last_index;
754  m_last_emin = model.m_last_emin;
755  m_last_emax = model.m_last_emax;
757 
758  // Return
759  return;
760 }
761 
762 
763 /***********************************************************************//**
764  * @brief Delete class members
765  ***************************************************************************/
767 {
768  // Return
769  return;
770 }
771 
772 
773 /***********************************************************************//**
774  * @brief Update precomputed values
775  *
776  * @param[in] srcEng Source energy
777  ***************************************************************************/
779 {
780  // Compute index+1
781  double gamma = index() + 2.0;
782 
783  // Change in spectral index?
784  if (index() != m_last_index) {
785 
786  // Save actual spectral index
787  m_last_index = index();
788 
789  // Change in energy boundaries?
790  if (emin() != m_last_emin || emax() != m_last_emax) {
791  m_log_emin = std::log(emin().MeV());
792  m_last_emin = emin();
793  m_log_emax = std::log(emax().MeV());
794  m_last_emax = emax();
795  }
796 
797  // Compute normalization factors
798  if (gamma != 0.0) {
799  m_pow_emin = std::pow(emin().MeV(), gamma);
800  m_pow_emax = std::pow(emax().MeV(), gamma);
801  double d = m_pow_emax - m_pow_emin;
802  m_norm = gamma / d;
803  m_g_norm = 1.0/gamma -
804  (m_pow_emax*m_log_emax - m_pow_emin*m_log_emin)/d;
805  }
806  else {
807  m_norm = 1.0 / (m_log_emax - m_log_emin);
808  m_g_norm = 0.0;
809  }
810 
811  // Update power law factor
812  m_power = std::pow(srcEng.MeV(), index());
813  m_last_energy = srcEng;
814 
815  } // endif: change in spectral index
816 
817  // ... no change in spectral index
818  else {
819 
820  // Change in energy boundaries?
821  if (emin() != m_last_emin || emax() != m_last_emax) {
822 
823  // Update energy boundaries
824  m_log_emin = std::log(emin().MeV());
825  m_last_emin = emin();
826  m_log_emax = std::log(emax().MeV());
827  m_last_emax = emax();
828 
829  // Compute power law normalization
830  if (gamma != 0.0) {
831  m_pow_emin = std::pow(emin().MeV(), gamma);
832  m_pow_emax = std::pow(emax().MeV(), gamma);
833  double d = m_pow_emax - m_pow_emin;
834  m_norm = gamma / d;
835  m_g_norm = 1.0/gamma -
836  (m_pow_emax*m_log_emax - m_pow_emin*m_log_emin)/d;
837  }
838  else {
839  m_norm = 1.0 / (m_log_emax - m_log_emin);
840  m_g_norm = 0.0;
841  }
842 
843  } // endif: change in energy boundaries
844 
845  // Change in energy?
846  if (srcEng != m_last_energy) {
847  m_power = std::pow(srcEng.MeV(), index());
848  m_last_energy = srcEng;
849  }
850 
851  } // endelse: no change in spectral index
852 
853  // Return
854  return;
855 }
const double erg2MeV
Definition: GTools.hpp:46
virtual void write(GXmlElement &xml) const
Write model into XML element.
double m_last_index
Last spectral index (MeV)
const double & factor_gradient(void) const
Return parameter factor gradient.
double norm(const GVector &vector)
Computes vector norm.
Definition: GVector.cpp:864
const std::string & name(void) const
Return parameter name.
Random number generator class definition.
Abstract spectral model base class.
double gradient(void) const
Return parameter gradient.
int size(void) const
Return number of parameters.
virtual GModelSpectral & operator=(const GModelSpectral &model)
Assignment operator.
void write(GXmlElement &xml) const
Set or update parameter attributes in XML element.
Definition: GModelPar.cpp:351
std::vector< GModelPar * > m_pars
Parameter pointers.
XML element node class.
Definition: GXmlElement.hpp:48
Spectral model registry class definition.
GEnergy emin(void) const
Return minimum energy.
Random number generator class.
Definition: GRan.hpp:44
double MeV(void) const
Return energy in MeV.
Definition: GEnergy.cpp:321
Time class.
Definition: GTime.hpp:55
Gammalib tools definition.
void init_members(void)
Initialise class members.
virtual GEnergy mc(const GEnergy &emin, const GEnergy &emax, const GTime &time, GRan &ran) const
Returns MC energy between [emin, emax].
Energy flux normalized power law spectral model class interface definition.
virtual ~GModelSpectralPlawEnergyFlux(void)
Destructor.
bool is_free(void) const
Signal if parameter is free.
virtual GModelSpectralPlawEnergyFlux & operator=(const GModelSpectralPlawEnergyFlux &model)
Assignment operator.
virtual GModelSpectralPlawEnergyFlux * clone(void) const
Clone power law model.
const double ln10
Definition: GMath.hpp:46
double log10MeV(void) const
Return log10 of energy in MeV.
Definition: GEnergy.cpp:423
GModelPar m_emin
Lower energy limit (MeV)
void update(const GEnergy &srcEng) const
Update precomputed values.
bool is_notanumber(const double &x)
Signal if argument is not a number.
Definition: GTools.hpp:201
const double & scale(void) const
Return parameter scale.
bool is_infinite(const double &x)
Signal if argument is infinite.
Definition: GTools.hpp:184
GModelPar m_eflux
Energy flux (erg/cm2/s)
GEnergy m_last_emax
Last upper energy limit.
bool has_grad(void) const
Signal if parameter gradient is computed analytically.
GEnergy m_last_emin
Last lower energy limit.
virtual void read(const GXmlElement &xml)
Read model from XML element.
virtual std::string type(void) const
Return model type.
double m_g_norm
Power-law normalization gradient.
void free(void)
Free a parameter.
void fix(void)
Fix a parameter.
GXmlElement * xml_need_par(const std::string &origin, GXmlElement &xml, const std::string &name)
Return pointer to parameter with given name in XML element.
Definition: GTools.cpp:1637
GVector log(const GVector &vector)
Computes natural logarithm of vector elements.
Definition: GVector.cpp:1274
double uniform(void)
Returns random double precision floating value in range 0 to 1.
Definition: GRan.cpp:242
void check_energy_interval(const std::string &origin, const GEnergy &emin, const GEnergy &emax)
Checks energy interval.
Definition: GException.cpp:364
void clear(void)
Clear parameter.
GModelPar m_emax
Upper energy limit (MeV)
GModelSpectralPlawEnergyFlux(void)
Void constructor.
GChatter
Definition: GTypemaps.hpp:33
virtual double flux(const GEnergy &emin, const GEnergy &emax) const
Returns model photon flux between emin, emax
void xml_check_parnum(const std::string &origin, const GXmlElement &xml, const int &number)
Checks number of parameters.
Definition: GTools.cpp:1777
Interface definition for the spectral model registry class.
GEnergy m_last_energy
Last source energy.
virtual double eval(const GEnergy &srcEng, const GTime &srcTime=GTime(), const bool &gradients=false) const
Evaluate function.
void init_members(void)
Initialise class members.
void copy_members(const GModelSpectralPlawEnergyFlux &model)
Copy class members.
double m_norm
Power-law normalization (for pivot energy 1 MeV)
void range(const double &min, const double &max)
Set minimum and maximum parameter boundaries.
void read(const GXmlElement &xml)
Extract parameter attributes from XML element.
Definition: GModelPar.cpp:229
double value(void) const
Return parameter value.
double index(void) const
Return power law index.
const std::string & unit(void) const
Return parameter unit.
GVector pow(const GVector &vector, const double &power)
Computes tanh of vector elements.
Definition: GVector.cpp:1422
void free_members(void)
Delete class members.
const GModelSpectralPlawEnergyFlux g_spectral_plaw_eflux_seed("PowerLaw","EnergyFlux","Index","LowerLimit","UpperLimit")
Exception handler interface definition.
GVector exp(const GVector &vector)
Computes exponential of vector elements.
Definition: GVector.cpp:1232
double eflux(void) const
Return energy flux.
std::string parformat(const std::string &s, const int &indent=0)
Convert string in parameter format.
Definition: GTools.cpp:1143
Energy flux normalized power law spectral model class.
virtual std::string print(const GChatter &chatter=NORMAL) const
Print power law information.
GEnergy emax(void) const
Return maximum energy.
const GXmlElement * xml_get_par(const std::string &origin, const GXmlElement &xml, const std::string &name)
Return pointer to parameter with given name in XML element.
Definition: GTools.cpp:1689
void free_members(void)
Delete class members.
virtual void clear(void)
Clear power law model.
const double & factor_value(void) const
Return parameter factor value.
Mathematical function definitions.
Class that handles energies in a unit independent way.
Definition: GEnergy.hpp:48
std::string str(const unsigned short int &value)
Convert unsigned short integer value into string.
Definition: GTools.cpp:489
void xml_check_type(const std::string &origin, GXmlElement &xml, const std::string &type)
Checks the model type.
Definition: GTools.cpp:1819