Commit 37b8b1c944e2f140033e6985ec99a1e37d3c149f
1 parent
2a198690
Replace log flag by string in GEbounds class (#2881)
Showing
10 changed files
with
357 additions
and
145 deletions
ChangeLog
| ... | ... | @@ -27,6 +27,7 @@ |
| 27 | 27 | Fix GTime.utc() precision bug (#2917) |
| 28 | 28 | Add GTime.datetime() method and add optional precision to GTime.utc() (#2909) |
| 29 | 29 | Remove obsolete methods from GCTAResponseCache class (#2893) |
| 30 | + Replace log flag by string in GEbounds class (#2881) | |
| 30 | 31 | Allow RoI centres different from pointing direction in unbinned analysis |
| 31 | 32 | (#2695) |
| 32 | 33 | Add GSkyDir::moon() method (#1855) | ... | ... |
NEWS
| ... | ... | @@ -46,7 +46,8 @@ The following methods have been added: |
| 46 | 46 | - GSkyMap::extract() - Extract section of sky map |
| 47 | 47 | - GSkyMap::region_circle() - Get bounding region circle of sky map |
| 48 | 48 | - GSkyRegionCircle::operator==() - Equality operator |
| 49 | -- GSkyRegionCircle::operator!=() - Non-equality operator | |
| 49 | +- GSkyRegionCircle::operator!=() - Non-equality operator | |
| 50 | +- GEbounds::set() - Set energy boundaries for different methods | |
| 50 | 51 | - GModelPar::has_factor_min() - Test if parameter has factor minimum |
| 51 | 52 | - GModelPar::has_factor_max() - Test if parameter has factor maximum |
| 52 | 53 | - GModelPar::remove_factor_min - Remove factor minimum |
| ... | ... | @@ -64,6 +65,8 @@ The following methods have been added: |
| 64 | 65 | - GCOMDri::cone_content() - Get DRI content within event cone |
| 65 | 66 | |
| 66 | 67 | The following methods have been removed: |
| 68 | +- GEbounds::set_lin() - method is now private | |
| 69 | +- GEbounds::set_log() - method is now private | |
| 67 | 70 | - GModelSpatialDiffuseCube::maps() |
| 68 | 71 | - GModelSpatialDiffuseCube::pixels() |
| 69 | 72 | |
| ... | ... | @@ -78,6 +81,7 @@ The arguments for the following methods have been changed: |
| 78 | 81 | - GTime::utc(int&) - Add optional precision value |
| 79 | 82 | - GSkyDir::posang(GSkyDir&, std::string&) - Add optional coordinate system string |
| 80 | 83 | - GSkyDir::posang_dir(GSkyDir&, std::string&) - Add optional coordinate system string |
| 84 | +- GEbounds::GEbounds(int&, GEnergy&, GEnergy&, std::string&, double&) - Replace bool by string and double | |
| 81 | 85 | |
| 82 | 86 | The return value of the following methods has been changed: |
| 83 | 87 | - none |
| ... | ... | @@ -178,6 +182,14 @@ Add GTime.datetime() method to the Python interface to convert times from and |
| 178 | 182 | to datetime.datetime objects. Add an optional precision argument to the GTime.utc() |
| 179 | 183 | to set the number of digits after the comma for the seconds (#2909). |
| 180 | 184 | |
| 185 | +The interface of the GEbounds constructor that sets a given number of energy | |
| 186 | +boundaries was changed. The bool argument that toggled between linear and | |
| 187 | +logarithmic spacing was replaced by a string that can take the values "LIN", | |
| 188 | +"LOG" or "POW". For the "POW" method an additional optional argument was added | |
| 189 | +to specify the power-law index. The GEbounds::set() method was added with the | |
| 190 | +same method arguments, and the former set_lin() and set_log() methods were | |
| 191 | +made private (#2881). | |
| 192 | + | |
| 181 | 193 | Add GTime.julian_epoch() methods that return the Julian epoch for a given time |
| 182 | 194 | (#1854). |
| 183 | 195 | ... | ... |
doc/source/admin/release_history/1.7.rst
| ... | ... | @@ -55,6 +55,8 @@ Improvements |
| 55 | 55 | * Add ``GGti::overlap()`` method. |
| 56 | 56 | * [`2909 <https://cta-redmine.irap.omp.eu/issues/2909>`_] - |
| 57 | 57 | Add ``GTime.datetime()`` method and add optional precision to ``GTime.utc()`` method. |
| 58 | +* [`2881 <https://cta-redmine.irap.omp.eu/issues/2881>`_] - | |
| 59 | + Replace ``log`` flag by ``string`` in ``GEbounds`` class. | |
| 58 | 60 | * [`2695 <https://cta-redmine.irap.omp.eu/issues/2695>`_] - |
| 59 | 61 | Allow RoI centres different from pointing direction in unbinned analysis. |
| 60 | 62 | * [`1855 <https://cta-redmine.irap.omp.eu/issues/1855>`_] - | ... | ... |
include/GEbounds.hpp
| 1 | 1 | /*************************************************************************** |
| 2 | 2 | * GEbounds.hpp - Energy boundaries class * |
| 3 | 3 | * ----------------------------------------------------------------------- * |
| 4 | - * copyright (C) 2009-2017 by Juergen Knoedlseder * | |
| 4 | + * copyright (C) 2009-2020 by Juergen Knoedlseder * | |
| 5 | 5 | * ----------------------------------------------------------------------- * |
| 6 | 6 | * * |
| 7 | 7 | * This program is free software: you can redistribute it and/or modify * |
| ... | ... | @@ -71,8 +71,11 @@ public: |
| 71 | 71 | explicit GEbounds(const GEnergies& energies); |
| 72 | 72 | GEbounds(const GEbounds& ebds); |
| 73 | 73 | GEbounds(const GEnergy& emin, const GEnergy& emax); |
| 74 | - GEbounds(const int& num, const GEnergy& emin, const GEnergy& emax, | |
| 75 | - const bool& log = true); | |
| 74 | + GEbounds(const int& num, | |
| 75 | + const GEnergy& emin, | |
| 76 | + const GEnergy& emax, | |
| 77 | + const std::string& method = "LOG", | |
| 78 | + const double& gamma = 1.0); | |
| 76 | 79 | virtual ~GEbounds(void); |
| 77 | 80 | |
| 78 | 81 | // Operators |
| ... | ... | @@ -92,8 +95,11 @@ public: |
| 92 | 95 | void reserve(const int& num); |
| 93 | 96 | void extend(const GEbounds& ebds); |
| 94 | 97 | void set(const GEnergies& energies); |
| 95 | - void set_lin(const int& num, const GEnergy& emin, const GEnergy& emax); | |
| 96 | - void set_log(const int& num, const GEnergy& emin, const GEnergy& emax); | |
| 98 | + void set(const int& num, | |
| 99 | + const GEnergy& emin, | |
| 100 | + const GEnergy& emax, | |
| 101 | + const std::string& method = "LOG", | |
| 102 | + const double& gamma = 1.0); | |
| 97 | 103 | void load(const GFilename& filename); |
| 98 | 104 | void save(const GFilename& filename, |
| 99 | 105 | const bool& clobber = false, |
| ... | ... | @@ -118,7 +124,6 @@ public: |
| 118 | 124 | bool contains(const GEnergy& emin, const GEnergy& emax) const; |
| 119 | 125 | std::string print(const GChatter& chatter = NORMAL) const; |
| 120 | 126 | |
| 121 | - | |
| 122 | 127 | protected: |
| 123 | 128 | // Protected methods |
| 124 | 129 | void init_members(void); |
| ... | ... | @@ -126,6 +131,11 @@ protected: |
| 126 | 131 | void free_members(void); |
| 127 | 132 | void set_attributes(void); |
| 128 | 133 | void insert_eng(const int& index, const GEnergy& emin, const GEnergy& emax); |
| 134 | + void set_lin(const int& num, const GEnergy& emin, const GEnergy& emax); | |
| 135 | + void set_log(const int& num, const GEnergy& emin, const GEnergy& emax); | |
| 136 | + void set_pow(const int& num, const GEnergy& emin, const GEnergy& emax, | |
| 137 | + const double& gamma); | |
| 138 | + | |
| 129 | 139 | |
| 130 | 140 | // Protected data area |
| 131 | 141 | int m_num; //!< Number of energy boundaries | ... | ... |
inst/cta/src/GCTAModelAeffBackground.cpp
| ... | ... | @@ -563,8 +563,10 @@ GCTAEventList* GCTAModelAeffBackground::mc(const GObservation& obs, |
| 563 | 563 | // a fixed energy sampling for an instance of GModelSpectralNodes. |
| 564 | 564 | // This is analogous to to the GCTAModelIrfBackground::mc method. |
| 565 | 565 | // We make sure that only non-negative nodes get appended. |
| 566 | - GEbounds spectral_ebounds = | |
| 567 | - GEbounds(m_n_mc_energies, ebounds.emin(), ebounds.emax(), true); | |
| 566 | + GEbounds spectral_ebounds(m_n_mc_energies, | |
| 567 | + ebounds.emin(), | |
| 568 | + ebounds.emax(), | |
| 569 | + "LOG"); | |
| 568 | 570 | GModelSpectralNodes spectral; |
| 569 | 571 | for (int i = 0; i < spectral_ebounds.size(); ++i) { |
| 570 | 572 | GEnergy energy = spectral_ebounds.elogmean(i); | ... | ... |
pyext/GEbounds.i
| 1 | 1 | /*************************************************************************** |
| 2 | 2 | * GEbounds.i - Energy boundaries class * |
| 3 | 3 | * ----------------------------------------------------------------------- * |
| 4 | - * copyright (C) 2010-2018 by Juergen Knoedlseder * | |
| 4 | + * copyright (C) 2010-2020 by Juergen Knoedlseder * | |
| 5 | 5 | * ----------------------------------------------------------------------- * |
| 6 | 6 | * * |
| 7 | 7 | * This program is free software: you can redistribute it and/or modify * |
| ... | ... | @@ -49,8 +49,11 @@ public: |
| 49 | 49 | explicit GEbounds(const GEnergies& energies); |
| 50 | 50 | GEbounds(const GEbounds& ebds); |
| 51 | 51 | GEbounds(const GEnergy& emin, const GEnergy& emax); |
| 52 | - GEbounds(const int& num, const GEnergy& emin, const GEnergy& emax, | |
| 53 | - const bool& log = true); | |
| 52 | + GEbounds(const int& num, | |
| 53 | + const GEnergy& emin, | |
| 54 | + const GEnergy& emax, | |
| 55 | + const std::string& method = "LOG", | |
| 56 | + const double& gamma = 1.0); | |
| 54 | 57 | virtual ~GEbounds(void); |
| 55 | 58 | |
| 56 | 59 | // Methods |
| ... | ... | @@ -67,8 +70,11 @@ public: |
| 67 | 70 | void reserve(const int& num); |
| 68 | 71 | void extend(const GEbounds& ebds); |
| 69 | 72 | void set(const GEnergies& energies); |
| 70 | - void set_lin(const int& num, const GEnergy& emin, const GEnergy& emax); | |
| 71 | - void set_log(const int& num, const GEnergy& emin, const GEnergy& emax); | |
| 73 | + void set(const int& num, | |
| 74 | + const GEnergy& emin, | |
| 75 | + const GEnergy& emax, | |
| 76 | + const std::string& method = "LOG", | |
| 77 | + const double& gamma = 1.0); | |
| 72 | 78 | void load(const GFilename& filename); |
| 73 | 79 | void save(const GFilename& filename, |
| 74 | 80 | const bool& clobber = false, | ... | ... |
src/obs/GEbounds.cpp
| 1 | 1 | /*************************************************************************** |
| 2 | 2 | * GEbounds.cpp - Energy boundary class * |
| 3 | 3 | * ----------------------------------------------------------------------- * |
| 4 | - * copyright (C) 2009-2017 by Juergen Knoedlseder * | |
| 4 | + * copyright (C) 2009-2020 by Juergen Knoedlseder * | |
| 5 | 5 | * ----------------------------------------------------------------------- * |
| 6 | 6 | * * |
| 7 | 7 | * This program is free software: you can redistribute it and/or modify * |
| ... | ... | @@ -41,8 +41,8 @@ |
| 41 | 41 | #include "GXmlElement.hpp" |
| 42 | 42 | |
| 43 | 43 | /* __ Method name definitions ____________________________________________ */ |
| 44 | -#define G_SET_LIN "GEbounds::set_lin(int&, GEnergy&, GEnergy&)" | |
| 45 | -#define G_SET_LOG "GEbounds::set_log(int&, GEnergy&, GEnergy&)" | |
| 44 | +#define G_SET "GEbounds::set(int&, GEnergy&, GEnergy&, std::string&, "\ | |
| 45 | + "double&)" | |
| 46 | 46 | #define G_READ_XML "GEbounds::read(GXmlElement&)" |
| 47 | 47 | #define G_WRITE_XML "GEbounds::write(GXmlElement&)" |
| 48 | 48 | #define G_REMOVE "GEbounds::remove(int&)" |
| ... | ... | @@ -54,6 +54,9 @@ |
| 54 | 54 | #define G_ELOGMEAN "GEbounds::elogmean(int&)" |
| 55 | 55 | #define G_EWIDTH "GEbounds::ewidth(int&)" |
| 56 | 56 | #define G_INSERT_ENG "GEbounds::insert_eng(int&, GEnergy&, GEnergy&)" |
| 57 | +#define G_SET_LIN "GEbounds::set_lin(int&, GEnergy&, GEnergy&)" | |
| 58 | +#define G_SET_LOG "GEbounds::set_log(int&, GEnergy&, GEnergy&)" | |
| 59 | +#define G_SET_POW "GEbounds::set_pow(int&, GEnergy&, GEnergy&, double&)" | |
| 57 | 60 | |
| 58 | 61 | /* __ Macros _____________________________________________________________ */ |
| 59 | 62 | |
| ... | ... | @@ -186,25 +189,25 @@ GEbounds::GEbounds(const GEnergy& emin, const GEnergy& emax) |
| 186 | 189 | * @param[in] num Number of energy intervals. |
| 187 | 190 | * @param[in] emin Minimum energy of first interval. |
| 188 | 191 | * @param[in] emax Maximum energy of last interval. |
| 189 | - * @param[in] log Use logarithmic spacing? (defaults to true). | |
| 192 | + * @param[in] method Energy spacing method (one of "LIN", "LOG" or "POW"). | |
| 193 | + * @param[in] gamma Power law index for @p POW method. | |
| 190 | 194 | * |
| 191 | 195 | * Constructs energy boundaries by defining @p num successive energy |
| 192 | - * intervals between @p emin and @p emax. The @p log parameter controls | |
| 193 | - * whether the energy spacing is logarihmic (default) or linear. | |
| 196 | + * intervals between @p emin and @p emax. The @p method parameter controls | |
| 197 | + * the energy spacing of the energy boundaries. See the set() method for | |
| 198 | + * more information. | |
| 194 | 199 | ***************************************************************************/ |
| 195 | -GEbounds::GEbounds(const int& num, const GEnergy& emin, const GEnergy& emax, | |
| 196 | - const bool& log) | |
| 200 | +GEbounds::GEbounds(const int& num, | |
| 201 | + const GEnergy& emin, | |
| 202 | + const GEnergy& emax, | |
| 203 | + const std::string& method, | |
| 204 | + const double& gamma) | |
| 197 | 205 | { |
| 198 | 206 | // Initialise members |
| 199 | 207 | init_members(); |
| 200 | 208 | |
| 201 | 209 | // Set intervals |
| 202 | - if (log) { | |
| 203 | - this->set_log(num, emin, emax); | |
| 204 | - } | |
| 205 | - else { | |
| 206 | - this->set_lin(num, emin, emax); | |
| 207 | - } | |
| 210 | + set(num, emin, emax, method, gamma); | |
| 208 | 211 | |
| 209 | 212 | // Return |
| 210 | 213 | return; |
| ... | ... | @@ -572,119 +575,44 @@ void GEbounds::set(const GEnergies& energies) |
| 572 | 575 | * @param[in] num Number of energy intervals. |
| 573 | 576 | * @param[in] emin Minimum energy of first interval. |
| 574 | 577 | * @param[in] emax Maximum energy of last interval. |
| 578 | + * @param[in] method Energy spacing method (one of "LIN", "LOG" or "POW"). | |
| 579 | + * @param[in] gamma Power law index for @p POW method. | |
| 575 | 580 | * |
| 576 | 581 | * @exception GException::invalid_argument |
| 577 | 582 | * Minimum energy is larger than the maximum energy. |
| 578 | 583 | * |
| 579 | - * Creates @p num linearly spaced energy boundaries running from @p emin to | |
| 580 | - * @p emax. If @p num is not a positive integer, no energy | |
| 581 | - * boundaries will be set. | |
| 582 | - ***************************************************************************/ | |
| 583 | -void GEbounds::set_lin(const int& num, const GEnergy& emin, const GEnergy& emax) | |
| 584 | -{ | |
| 585 | - // Initialise members | |
| 586 | - clear(); | |
| 587 | - | |
| 588 | - // Continue only if the requested number of energy boundaries is positive | |
| 589 | - if (num > 0) { | |
| 590 | - | |
| 591 | - // Throw an exception if the maximum energy is smaller than the | |
| 592 | - // minimum energy | |
| 593 | - if (emin > emax) { | |
| 594 | - std::string msg = "Minimum energy "+emin.print()+" is larger than " | |
| 595 | - "maximum energy "+emax.print()+". Please provide " | |
| 596 | - "a minimum energy that is not larger than the " | |
| 597 | - "maximum energy."; | |
| 598 | - throw GException::invalid_argument(G_SET_LIN, msg); | |
| 599 | - } | |
| 600 | - | |
| 601 | - // Compute bin width | |
| 602 | - GEnergy ebin = (emax - emin)/double(num); | |
| 603 | - | |
| 604 | - // Append boundaries | |
| 605 | - GEnergy min = emin; | |
| 606 | - GEnergy max = emin + ebin; | |
| 607 | - for (int i = 0; i < num; ++i) { | |
| 608 | - append(min, max); | |
| 609 | - min += ebin; | |
| 610 | - max += ebin; | |
| 611 | - } | |
| 612 | - | |
| 613 | - // Set attributes | |
| 614 | - set_attributes(); | |
| 615 | - | |
| 616 | - } // endif: number of energy boundaries was positive | |
| 617 | - | |
| 618 | - // Return | |
| 619 | - return; | |
| 620 | -} | |
| 621 | - | |
| 622 | - | |
| 623 | -/***********************************************************************//** | |
| 624 | - * @brief Set logarithmically spaced energy intervals | |
| 625 | - * | |
| 626 | - * @param[in] num Number of energy intervals. | |
| 627 | - * @param[in] emin Minimum energy of first interval. | |
| 628 | - * @param[in] emax Maximum energy of last interval. | |
| 584 | + * Sets energy boundaries by defining @p num successive energy intervals | |
| 585 | + * between @p emin and @p emax. The @p method parameter controls the energy | |
| 586 | + * spacing of the energy boundaries. See the set_lin(), set_log() and | |
| 587 | + * set_pow() methods for more information. | |
| 629 | 588 | * |
| 630 | - * @exception GException::invalid_argument | |
| 631 | - * Minimum or maximum energy are not positive or minimum energy | |
| 632 | - * is larger than the maximum energy. | |
| 633 | - * | |
| 634 | - * Creates @p num logarithmically spaced energy boundaries running from | |
| 635 | - * @p emin to @p emax. If @p num is not a positive integer, no energy | |
| 636 | - * boundaries will be set. | |
| 589 | + * If @p num is not a positive integer, no energy boundaries will be set. | |
| 637 | 590 | ***************************************************************************/ |
| 638 | -void GEbounds::set_log(const int& num, const GEnergy& emin, const GEnergy& emax) | |
| 591 | +void GEbounds::set(const int& num, | |
| 592 | + const GEnergy& emin, | |
| 593 | + const GEnergy& emax, | |
| 594 | + const std::string& method, | |
| 595 | + const double& gamma) | |
| 639 | 596 | { |
| 640 | - // Initialise members | |
| 641 | - clear(); | |
| 597 | + // Convert method to upper-case string | |
| 598 | + std::string umethod = gammalib::toupper(method); | |
| 642 | 599 | |
| 643 | - // Continue only if the requested number of energy boundaries is positive | |
| 644 | - if (num > 0) { | |
| 645 | - | |
| 646 | - // Throw an exception if the minimum or maximum energy is not positive | |
| 647 | - if (emin.MeV() <= 0.0) { | |
| 648 | - std::string msg = "Non-positive minimum energy "+emin.print()+ | |
| 649 | - " specified. Please provide a positive minimum " | |
| 650 | - "energy value."; | |
| 651 | - throw GException::invalid_argument(G_SET_LOG, msg); | |
| 652 | - } | |
| 653 | - if (emax.MeV() <= 0.0) { | |
| 654 | - std::string msg = "Non-positive maximum energy "+emax.print()+ | |
| 655 | - " specified. Please provide a positive minimum " | |
| 656 | - "energy value."; | |
| 657 | - throw GException::invalid_argument(G_SET_LOG, msg); | |
| 658 | - } | |
| 659 | - | |
| 660 | - // Throw an exception if the maximum energy is smaller than the | |
| 661 | - // minimum energy | |
| 662 | - if (emin > emax) { | |
| 663 | - std::string msg = "Minimum energy "+emin.print()+" is larger than " | |
| 664 | - "maximum energy "+emax.print()+". Please provide " | |
| 665 | - "a minimum energy that is not larger than the " | |
| 666 | - "maximum energy."; | |
| 667 | - throw GException::invalid_argument(G_SET_LOG, msg); | |
| 668 | - } | |
| 669 | - | |
| 670 | - // Compute bin width | |
| 671 | - double elogmin = std::log10(emin.MeV()); | |
| 672 | - double elogmax = std::log10(emax.MeV()); | |
| 673 | - double elogbin = (elogmax - elogmin)/double(num); | |
| 674 | - | |
| 675 | - // Append boundaries | |
| 676 | - GEnergy min; | |
| 677 | - GEnergy max; | |
| 678 | - for (int i = 0; i < num; ++i) { | |
| 679 | - min.MeV(std::pow(10.0, double(i)*elogbin + elogmin)); | |
| 680 | - max.MeV(std::pow(10.0, double(i+1)*elogbin + elogmin)); | |
| 681 | - append(min, max); | |
| 682 | - } | |
| 683 | - | |
| 684 | - // Set attributes | |
| 685 | - set_attributes(); | |
| 686 | - | |
| 687 | - } // endif: number of energy boundaries was positive | |
| 600 | + // Dispatch to corresponding set methos | |
| 601 | + if (umethod == "LIN") { | |
| 602 | + set_lin(num, emin, emax); | |
| 603 | + } | |
| 604 | + else if (umethod == "LOG") { | |
| 605 | + set_log(num, emin, emax); | |
| 606 | + } | |
| 607 | + else if (umethod == "POW") { | |
| 608 | + set_pow(num, emin, emax, gamma); | |
| 609 | + } | |
| 610 | + else { | |
| 611 | + std::string msg = "Invalid energy spacing method \""+umethod+"\" " | |
| 612 | + "specified. Please provide one of \"LIN\", \"LOG\"" | |
| 613 | + ", or \"POW\"."; | |
| 614 | + throw GException::invalid_argument(G_SET, msg); | |
| 615 | + } | |
| 688 | 616 | |
| 689 | 617 | // Return |
| 690 | 618 | return; |
| ... | ... | @@ -1458,6 +1386,245 @@ void GEbounds::insert_eng(const int& index, |
| 1458 | 1386 | } |
| 1459 | 1387 | |
| 1460 | 1388 | |
| 1389 | +/***********************************************************************//** | |
| 1390 | + * @brief Set linearly spaced energy intervals | |
| 1391 | + * | |
| 1392 | + * @param[in] num Number of energy intervals. | |
| 1393 | + * @param[in] emin Minimum energy of first interval. | |
| 1394 | + * @param[in] emax Maximum energy of last interval. | |
| 1395 | + * | |
| 1396 | + * @exception GException::invalid_argument | |
| 1397 | + * Minimum energy is larger than the maximum energy. | |
| 1398 | + * | |
| 1399 | + * Creates \f$N\f$ linearly spaced energy boundaries running from | |
| 1400 | + * \f$E_{\rm min}\f$ to \f$E_{\rm max}\f$ defined by | |
| 1401 | + * | |
| 1402 | + * \f[ | |
| 1403 | + * E_{\rm min}^{(i)} = E_{\rm min} + \frac{E_{\rm max} - E_{\rm min}}{N} | |
| 1404 | + * \times i | |
| 1405 | + * \f] | |
| 1406 | + * | |
| 1407 | + * and | |
| 1408 | + * | |
| 1409 | + * \f[ | |
| 1410 | + * E_{\rm max}^{(i)} = E_{\rm min} + \frac{E_{\rm max} - E_{\rm min}}{N} | |
| 1411 | + * \times (i + 1) | |
| 1412 | + * \f] | |
| 1413 | + * | |
| 1414 | + * If @p num is not positive the method will do nothing. | |
| 1415 | + ***************************************************************************/ | |
| 1416 | +void GEbounds::set_lin(const int& num, const GEnergy& emin, const GEnergy& emax) | |
| 1417 | +{ | |
| 1418 | + // Continue only if the requested number of energy boundaries is positive | |
| 1419 | + if (num > 0) { | |
| 1420 | + | |
| 1421 | + // Throw an exception if the maximum energy is smaller than the | |
| 1422 | + // minimum energy | |
| 1423 | + if (emin > emax) { | |
| 1424 | + std::string msg = "Minimum energy "+emin.print()+" is larger than " | |
| 1425 | + "maximum energy "+emax.print()+". Please provide " | |
| 1426 | + "a minimum energy that is not larger than the " | |
| 1427 | + "maximum energy."; | |
| 1428 | + throw GException::invalid_argument(G_SET_LIN, msg); | |
| 1429 | + } | |
| 1430 | + | |
| 1431 | + // Compute bin width | |
| 1432 | + GEnergy ebin = (emax - emin)/double(num); | |
| 1433 | + | |
| 1434 | + // Append boundaries | |
| 1435 | + GEnergy min = emin; | |
| 1436 | + GEnergy max = emin + ebin; | |
| 1437 | + for (int i = 0; i < num; ++i) { | |
| 1438 | + append(min, max); | |
| 1439 | + min += ebin; | |
| 1440 | + max += ebin; | |
| 1441 | + } | |
| 1442 | + | |
| 1443 | + // Set attributes | |
| 1444 | + set_attributes(); | |
| 1445 | + | |
| 1446 | + } // endif: number of energy boundaries was positive | |
| 1447 | + | |
| 1448 | + // Return | |
| 1449 | + return; | |
| 1450 | +} | |
| 1451 | + | |
| 1452 | + | |
| 1453 | +/***********************************************************************//** | |
| 1454 | + * @brief Set logarithmically spaced energy intervals | |
| 1455 | + * | |
| 1456 | + * @param[in] num Number of energy intervals. | |
| 1457 | + * @param[in] emin Minimum energy of first interval. | |
| 1458 | + * @param[in] emax Maximum energy of last interval. | |
| 1459 | + * | |
| 1460 | + * @exception GException::invalid_argument | |
| 1461 | + * Minimum or maximum energy are not positive or minimum energy | |
| 1462 | + * is larger than the maximum energy. | |
| 1463 | + * | |
| 1464 | + * Creates \f$N\f$ logarithmically spaced energy boundaries running from | |
| 1465 | + * \f$E_{\rm min}\f$ to \f$E_{\rm max}\f$ defined by | |
| 1466 | + * | |
| 1467 | + * \f[ | |
| 1468 | + * E_{\rm min}^{(i)} = 10^{\log_{10} E_{\rm min} + | |
| 1469 | + * \frac{\log_{10} E_{\rm max} - | |
| 1470 | + * \log_{10} E_{\rm min}}{N} | |
| 1471 | + * \times i} | |
| 1472 | + * \f] | |
| 1473 | + * | |
| 1474 | + * and | |
| 1475 | + * | |
| 1476 | + * \f[ | |
| 1477 | + * E_{\rm max}^{(i)} = 10^{\log_{10} E_{\rm min} + | |
| 1478 | + * \frac{\log_{10} E_{\rm max} - | |
| 1479 | + * \log_{10} E_{\rm min}}{N} | |
| 1480 | + * \times (i + 1)} | |
| 1481 | + * \f] | |
| 1482 | + * | |
| 1483 | + * If @p num is not positive the method will do nothing. | |
| 1484 | + ***************************************************************************/ | |
| 1485 | +void GEbounds::set_log(const int& num, const GEnergy& emin, const GEnergy& emax) | |
| 1486 | +{ | |
| 1487 | + // Initialise members | |
| 1488 | + clear(); | |
| 1489 | + | |
| 1490 | + // Continue only if the requested number of energy boundaries is positive | |
| 1491 | + if (num > 0) { | |
| 1492 | + | |
| 1493 | + // Throw an exception if the minimum or maximum energy is not positive | |
| 1494 | + if (emin.MeV() <= 0.0) { | |
| 1495 | + std::string msg = "Non-positive minimum energy "+emin.print()+ | |
| 1496 | + " specified. Please provide a positive minimum " | |
| 1497 | + "energy value."; | |
| 1498 | + throw GException::invalid_argument(G_SET_LOG, msg); | |
| 1499 | + } | |
| 1500 | + if (emax.MeV() <= 0.0) { | |
| 1501 | + std::string msg = "Non-positive maximum energy "+emax.print()+ | |
| 1502 | + " specified. Please provide a positive minimum " | |
| 1503 | + "energy value."; | |
| 1504 | + throw GException::invalid_argument(G_SET_LOG, msg); | |
| 1505 | + } | |
| 1506 | + | |
| 1507 | + // Throw an exception if the maximum energy is smaller than the | |
| 1508 | + // minimum energy | |
| 1509 | + if (emin > emax) { | |
| 1510 | + std::string msg = "Minimum energy "+emin.print()+" is larger than " | |
| 1511 | + "maximum energy "+emax.print()+". Please provide " | |
| 1512 | + "a minimum energy that is not larger than the " | |
| 1513 | + "maximum energy."; | |
| 1514 | + throw GException::invalid_argument(G_SET_LOG, msg); | |
| 1515 | + } | |
| 1516 | + | |
| 1517 | + // Compute bin width | |
| 1518 | + double elogmin = std::log10(emin.MeV()); | |
| 1519 | + double elogmax = std::log10(emax.MeV()); | |
| 1520 | + double elogbin = (elogmax - elogmin)/double(num); | |
| 1521 | + | |
| 1522 | + // Append boundaries | |
| 1523 | + GEnergy min; | |
| 1524 | + GEnergy max; | |
| 1525 | + for (int i = 0; i < num; ++i) { | |
| 1526 | + min.MeV(std::pow(10.0, double(i)*elogbin + elogmin)); | |
| 1527 | + max.MeV(std::pow(10.0, double(i+1)*elogbin + elogmin)); | |
| 1528 | + append(min, max); | |
| 1529 | + } | |
| 1530 | + | |
| 1531 | + // Set attributes | |
| 1532 | + set_attributes(); | |
| 1533 | + | |
| 1534 | + } // endif: number of energy boundaries was positive | |
| 1535 | + | |
| 1536 | + // Return | |
| 1537 | + return; | |
| 1538 | +} | |
| 1539 | + | |
| 1540 | + | |
| 1541 | +/***********************************************************************//** | |
| 1542 | + * @brief Set power-law spaced energy intervals | |
| 1543 | + * | |
| 1544 | + * @param[in] num Number of energy intervals. | |
| 1545 | + * @param[in] emin Minimum energy of first interval. | |
| 1546 | + * @param[in] emax Maximum energy of last interval. | |
| 1547 | + * @param[in] gamma Power law index. | |
| 1548 | + * | |
| 1549 | + * @exception GException::invalid_argument | |
| 1550 | + * Minimum or maximum energy are not positive or minimum energy | |
| 1551 | + * is larger than the maximum energy. | |
| 1552 | + * | |
| 1553 | + * Creates \f$N\f$ power-law spaced energy boundaries running from | |
| 1554 | + * \f$E_{\rm min}\f$ to \f$E_{\rm max}\f$. | |
| 1555 | + * | |
| 1556 | + * If @p num is not positive the method will do nothing. | |
| 1557 | + ***************************************************************************/ | |
| 1558 | +void GEbounds::set_pow(const int& num, | |
| 1559 | + const GEnergy& emin, | |
| 1560 | + const GEnergy& emax, | |
| 1561 | + const double& gamma) | |
| 1562 | +{ | |
| 1563 | + // Initialise members | |
| 1564 | + clear(); | |
| 1565 | + | |
| 1566 | + // Continue only if the requested number of energy boundaries is positive | |
| 1567 | + if (num > 0) { | |
| 1568 | + | |
| 1569 | + // Throw an exception if the minimum or maximum energy is not positive | |
| 1570 | + if (emin.MeV() <= 0.0) { | |
| 1571 | + std::string msg = "Non-positive minimum energy "+emin.print()+ | |
| 1572 | + " specified. Please provide a positive minimum " | |
| 1573 | + "energy value."; | |
| 1574 | + throw GException::invalid_argument(G_SET_POW, msg); | |
| 1575 | + } | |
| 1576 | + if (emax.MeV() <= 0.0) { | |
| 1577 | + std::string msg = "Non-positive maximum energy "+emax.print()+ | |
| 1578 | + " specified. Please provide a positive minimum " | |
| 1579 | + "energy value."; | |
| 1580 | + throw GException::invalid_argument(G_SET_POW, msg); | |
| 1581 | + } | |
| 1582 | + | |
| 1583 | + // Throw an exception if the maximum energy is smaller than the | |
| 1584 | + // minimum energy | |
| 1585 | + if (emin > emax) { | |
| 1586 | + std::string msg = "Minimum energy "+emin.print()+" is larger than " | |
| 1587 | + "maximum energy "+emax.print()+". Please provide " | |
| 1588 | + "a minimum energy that is not larger than the " | |
| 1589 | + "maximum energy."; | |
| 1590 | + throw GException::invalid_argument(G_SET_POW, msg); | |
| 1591 | + } | |
| 1592 | + | |
| 1593 | + // Precomputation | |
| 1594 | + double a = 1.0 - gamma; | |
| 1595 | + double c = (a == 0.0) ? 1.0 / (std::log(emax.MeV()) - std::log(emin.MeV())) | |
| 1596 | + : a / (std::pow(emax.MeV(),a) - std::pow(emin.MeV(),a)); | |
| 1597 | + //double b = double(c*(num-1.0)); | |
| 1598 | + double b = double(c*num); | |
| 1599 | + | |
| 1600 | + // Append boundaries | |
| 1601 | + double e = emin.MeV(); | |
| 1602 | + for (int i = 0; i < num; ++i) { | |
| 1603 | + | |
| 1604 | + // Compute upper bin boundary | |
| 1605 | + double log_e_next = (a == 0.0) | |
| 1606 | + ? 1.0/b + std::log(e) | |
| 1607 | + : std::log(a/b + std::pow(e,a)) / a; | |
| 1608 | + double e_next = std::exp(log_e_next); | |
| 1609 | + | |
| 1610 | + // Append energy bin | |
| 1611 | + append(GEnergy(e, "MeV"), GEnergy(e_next, "MeV")); | |
| 1612 | + | |
| 1613 | + // Store upper boundary as next lower boundary | |
| 1614 | + e = e_next; | |
| 1615 | + | |
| 1616 | + } | |
| 1617 | + | |
| 1618 | + // Set attributes | |
| 1619 | + set_attributes(); | |
| 1620 | + | |
| 1621 | + } // endif: number of energy boundaries was positive | |
| 1622 | + | |
| 1623 | + // Return | |
| 1624 | + return; | |
| 1625 | +} | |
| 1626 | + | |
| 1627 | + | |
| 1461 | 1628 | /*========================================================================== |
| 1462 | 1629 | = = |
| 1463 | 1630 | = Friends = | ... | ... |
test/test_GObservation.cpp
| ... | ... | @@ -201,7 +201,7 @@ void TestGObservation::test_ebounds(void) |
| 201 | 201 | |
| 202 | 202 | // Check linear boundaries |
| 203 | 203 | ebds.clear(); |
| 204 | - ebds.set_lin(2, GEnergy(1.0, "MeV"), GEnergy(3.0, "MeV")); | |
| 204 | + ebds.set(2, GEnergy(1.0, "MeV"), GEnergy(3.0, "MeV"), "LIN"); | |
| 205 | 205 | test_value(ebds.size(), 2, "GEbounds should have 2 elements."); |
| 206 | 206 | test_assert(!ebds.is_empty(), "GEbounds should not be empty."); |
| 207 | 207 | test_value(ebds.emin(0).MeV(), 1.0, 1.0e-10, "Bin 0 minimum energy should be 1."); |
| ... | ... | @@ -213,7 +213,19 @@ void TestGObservation::test_ebounds(void) |
| 213 | 213 | |
| 214 | 214 | // Check logarithmic boundaries |
| 215 | 215 | ebds.clear(); |
| 216 | - ebds.set_log(2, GEnergy(1.0, "MeV"), GEnergy(100.0, "MeV")); | |
| 216 | + ebds.set(2, GEnergy(1.0, "MeV"), GEnergy(100.0, "MeV"), "LOG"); | |
| 217 | + test_value(ebds.size(), 2, "GEbounds should have 2 elements."); | |
| 218 | + test_assert(!ebds.is_empty(), "GEbounds should not be empty."); | |
| 219 | + test_value(ebds.emin(0).MeV(), 1.0, 1.0e-10, "Bin 0 minimum energy should be 1."); | |
| 220 | + test_value(ebds.emin(1).MeV(), 10.0, 1.0e-10, "Bin 1 minimum energy should be 10."); | |
| 221 | + test_value(ebds.emax(0).MeV(), 10.0, 1.0e-10, "Bin 0 maximum energy should be 10."); | |
| 222 | + test_value(ebds.emax(1).MeV(), 100.0, 1.0e-10, "Bin 1 maximum energy should be 100."); | |
| 223 | + test_value(ebds.emin().MeV(), 1.0, 1.0e-10, "Minimum energy should be 1."); | |
| 224 | + test_value(ebds.emax().MeV(), 100.0, 1.0e-10, "Maximum energy should be 100."); | |
| 225 | + | |
| 226 | + // Check power-law boundaries | |
| 227 | + ebds.clear(); | |
| 228 | + ebds.set(2, GEnergy(1.0, "MeV"), GEnergy(100.0, "MeV"), "POW", 1.0); | |
| 217 | 229 | test_value(ebds.size(), 2, "GEbounds should have 2 elements."); |
| 218 | 230 | test_assert(!ebds.is_empty(), "GEbounds should not be empty."); |
| 219 | 231 | test_value(ebds.emin(0).MeV(), 1.0, 1.0e-10, "Bin 0 minimum energy should be 1."); |
| ... | ... | @@ -238,7 +250,7 @@ void TestGObservation::test_ebounds(void) |
| 238 | 250 | test_value(ebds.emax().MeV(), 1000.0, 1.0e-10, "Maximum energy should be 1000."); |
| 239 | 251 | |
| 240 | 252 | // Check emean, elogmean and ewidth methods |
| 241 | - ebds.set_log(1, GEnergy(1.0, "MeV"), GEnergy(10.0, "MeV")); | |
| 253 | + ebds.set(1, GEnergy(1.0, "MeV"), GEnergy(10.0, "MeV"), "LOG"); | |
| 242 | 254 | test_value(ebds.emean(0).MeV(), 5.5, 1.0e-10, "Mean energy should be 5.5."); |
| 243 | 255 | test_value(ebds.elogmean(0).MeV(), 3.16227766017, 1.0e-10, "Log mean energy should be 3.16227766017."); |
| 244 | 256 | test_value(ebds.ewidth(0).MeV(), 9.0, 1.0e-10, "Energy width should be 9.0."); |
| ... | ... | @@ -259,7 +271,7 @@ void TestGObservation::test_ebounds(void) |
| 259 | 271 | // Check constructing of linear invalid energy boundaries |
| 260 | 272 | test_try("Test constructing of linear invalid energy boundaries"); |
| 261 | 273 | try { |
| 262 | - GEbounds bad(10, GEnergy(100.0, "MeV"), GEnergy(10.0, "MeV"), false); | |
| 274 | + GEbounds bad(10, GEnergy(100.0, "MeV"), GEnergy(10.0, "MeV"), "LIN"); | |
| 263 | 275 | test_try_failure("Constructing of linear invalid energy boundaries " |
| 264 | 276 | "shall throw an exception."); |
| 265 | 277 | } |
| ... | ... | @@ -273,7 +285,7 @@ void TestGObservation::test_ebounds(void) |
| 273 | 285 | // Check constructing of logarithmic invalid energy boundaries |
| 274 | 286 | test_try("Test constructing of logarithmic invalid energy boundaries"); |
| 275 | 287 | try { |
| 276 | - GEbounds bad(10, GEnergy(100.0, "MeV"), GEnergy(10.0, "MeV"), true); | |
| 288 | + GEbounds bad(10, GEnergy(100.0, "MeV"), GEnergy(10.0, "MeV"), "LOG"); | |
| 277 | 289 | test_try_failure("Constructing of logarithmic invalid energy " |
| 278 | 290 | "boundaries shall throw an exception."); |
| 279 | 291 | } |
| ... | ... | @@ -287,7 +299,7 @@ void TestGObservation::test_ebounds(void) |
| 287 | 299 | // Check constructing of logarithmic invalid energy boundaries |
| 288 | 300 | test_try("Test constructing of logarithmic invalid energy boundaries"); |
| 289 | 301 | try { |
| 290 | - GEbounds bad(10, GEnergy(0.0, "MeV"), GEnergy(10.0, "MeV"), true); | |
| 302 | + GEbounds bad(10, GEnergy(0.0, "MeV"), GEnergy(10.0, "MeV"), "LOG"); | |
| 291 | 303 | test_try_failure("Constructing of logarithmic invalid energy " |
| 292 | 304 | "boundaries shall throw an exception."); |
| 293 | 305 | } |
| ... | ... | @@ -301,7 +313,7 @@ void TestGObservation::test_ebounds(void) |
| 301 | 313 | // Check constructing of logarithmic invalid energy boundaries |
| 302 | 314 | test_try("Test constructing of logarithmic invalid energy boundaries"); |
| 303 | 315 | try { |
| 304 | - GEbounds bad(10, GEnergy(10.0, "MeV"), GEnergy(0.0, "MeV"), true); | |
| 316 | + GEbounds bad(10, GEnergy(10.0, "MeV"), GEnergy(0.0, "MeV"), "LOG"); | |
| 305 | 317 | test_try_failure("Constructing of logarithmic invalid energy " |
| 306 | 318 | "boundaries shall throw an exception."); |
| 307 | 319 | } |
| ... | ... | @@ -1370,7 +1382,7 @@ void TestGObservation::test_energies(void) |
| 1370 | 1382 | test_value(energies[2].MeV(), 100.0, 1.0e-10, "Energy 2 should be 100 MeV."); |
| 1371 | 1383 | |
| 1372 | 1384 | // Check energy boundary set method |
| 1373 | - GEbounds ebds1(2, GEnergy(1.0, "MeV"), GEnergy(3.0, "MeV"), false); | |
| 1385 | + GEbounds ebds1(2, GEnergy(1.0, "MeV"), GEnergy(3.0, "MeV"), "LIN"); | |
| 1374 | 1386 | energies.set(ebds1); |
| 1375 | 1387 | test_value(energies.size(), 3, "GEbounds constructor (3 elements)"); |
| 1376 | 1388 | test_value(energies[0].MeV(), 1.0, 1.0e-10, "GEbounds constructor (3 elements)"); | ... | ... |
test/test_GObservation.py
| 1 | 1 | # ========================================================================== |
| 2 | 2 | # This module performs unit tests for the GammaLib observation module. |
| 3 | 3 | # |
| 4 | -# Copyright (C) 2012-2019 Juergen Knoedlseder | |
| 4 | +# Copyright (C) 2012-2020 Juergen Knoedlseder | |
| 5 | 5 | # |
| 6 | 6 | # This program is free software: you can redistribute it and/or modify |
| 7 | 7 | # it under the terms of the GNU General Public License as published by |
| ... | ... | @@ -361,7 +361,7 @@ class Test(gammalib.GPythonTestSuite): |
| 361 | 361 | """ |
| 362 | 362 | # Setup energies container |
| 363 | 363 | ebounds = gammalib.GEbounds(10, gammalib.GEnergy(1.0, 'MeV'), |
| 364 | - gammalib.GEnergy(11.0, 'MeV'), False) | |
| 364 | + gammalib.GEnergy(11.0, 'MeV'), 'LIN') | |
| 365 | 365 | |
| 366 | 366 | # Test ebounds[start:end] |
| 367 | 367 | self.test_value(len(ebounds[3:5]), 2) | ... | ... |
test/test_GXspec.cpp
| 1 | 1 | /*************************************************************************** |
| 2 | 2 | * test_GXspec.hpp - Test Xspec module * |
| 3 | 3 | * ----------------------------------------------------------------------- * |
| 4 | - * copyright (C) 2013-2017 by Juergen Knoedlseder * | |
| 4 | + * copyright (C) 2013-2020 by Juergen Knoedlseder * | |
| 5 | 5 | * ----------------------------------------------------------------------- * |
| 6 | 6 | * * |
| 7 | 7 | * This program is free software: you can redistribute it and/or modify * |
| ... | ... | @@ -88,7 +88,7 @@ void TestGXspec::test_GPha(void) |
| 88 | 88 | test_value(pha1.ancrfile(), "", "Check if empty PHA has empty ARF"); |
| 89 | 89 | |
| 90 | 90 | // Test energy boundary constructor, filling and accessing |
| 91 | - GEbounds ebds2(9, GEnergy(1.0, "TeV"), GEnergy(10.0, "TeV"), false); | |
| 91 | + GEbounds ebds2(9, GEnergy(1.0, "TeV"), GEnergy(10.0, "TeV"), "LIN"); | |
| 92 | 92 | GPha pha2(ebds2); |
| 93 | 93 | pha2.exposure(1234.5); |
| 94 | 94 | pha2.backfile("background"); | ... | ... |