GammaLib  2.1.0.dev
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
GModel.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  * GModel.cpp - Abstract virtual model base class *
3  * ----------------------------------------------------------------------- *
4  * copyright (C) 2009-2021 by Juergen Knoedlseder *
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 GModel.cpp
23  * @brief Abstract model base class implementation
24  * @author Juergen Knoedlseder
25  */
26 
27 /* __ Includes ___________________________________________________________ */
28 #ifdef HAVE_CONFIG_H
29 #include <config.h>
30 #endif
31 #include "GTools.hpp"
32 #include "GException.hpp"
33 #include "GModel.hpp"
34 
35 /* __ Method name definitions ____________________________________________ */
36 #define G_ACCESS "GModel::operator[](std::string&)"
37 #define G_AT "GModel::at(int&)"
38 #define G_SCALE "GModelPar& GModel::scale(int&)"
39 #define G_WRITE_SCALES "GModel::write_scales(GXmlElement&)"
40 
41 /* __ Macros _____________________________________________________________ */
42 
43 /* __ Coding definitions _________________________________________________ */
44 
45 /* __ Debug definitions __________________________________________________ */
46 
47 
48 /*==========================================================================
49  = =
50  = Constructors/destructors =
51  = =
52  ==========================================================================*/
53 
54 /***********************************************************************//**
55  * @brief Void constructor
56  ***************************************************************************/
58 {
59  // Initialise members
60  init_members();
61 
62  // Return
63  return;
64 }
65 
66 
67 /***********************************************************************//**
68  * @brief XML constructor
69  *
70  * @param[in] xml XML element.
71  *
72  * Construct model from XML element. The method extracts all model attributes
73  * from the XML file (see the read_attributes() method for more information
74  * about the supported attributes).
75  ***************************************************************************/
77 {
78  // Initialise members
79  init_members();
80 
81  // Read attributes
82  read_attributes(xml);
83 
84  // Return
85  return;
86 }
87 
88 
89 /***********************************************************************//**
90  * @brief Copy constructor
91  *
92  * @param[in] model Model.
93  ***************************************************************************/
94 GModel::GModel(const GModel& model)
95 {
96  // Initialise members
97  init_members();
98 
99  // Copy members
100  copy_members(model);
101 
102  // Return
103  return;
104 }
105 
106 
107 /***********************************************************************//**
108  * @brief Destructor
109  ***************************************************************************/
111 {
112  // Free members
113  free_members();
114 
115  // Return
116  return;
117 }
118 
119 
120 /*==========================================================================
121  = =
122  = Operators =
123  = =
124  ==========================================================================*/
125 
126 /***********************************************************************//**
127  * @brief Assignment operator
128  *
129  * @param[in] model Model.
130  * @return Model.
131  ***************************************************************************/
133 {
134  // Execute only if object is not identical
135  if (this != &model) {
136 
137  // Free members
138  free_members();
139 
140  // Initialise private members for clean destruction
141  init_members();
142 
143  // Copy members
144  copy_members(model);
145 
146  } // endif: object was not identical
147 
148  // Return
149  return *this;
150 }
151 
152 
153 /***********************************************************************//**
154  * @brief Returns reference to model parameter by name
155  *
156  * @param[in] name Parameter name.
157  * @return Reference to model parameter.
158  *
159  * @exception GException::invalid_argument
160  * Parameter with specified name not found.
161  *
162  * Returns a reference to the model parameter of the specified @p name.
163  * Throws an exception if no parameter with @p name is found.
164  ***************************************************************************/
165 GModelPar& GModel::operator[](const std::string& name)
166 {
167  // Get parameter index
168  int index = 0;
169  for (; index < size(); ++index) {
170  if (m_pars[index]->name() == name) {
171  break;
172  }
173  }
174 
175  // Throw exception if parameter name was not found
176  if (index >= size()) {
177  std::string msg = "Model parameter \""+name+"\" not found in model. "
178  "Please specify a valid model parameter name.";
180  }
181 
182  // Return reference
183  return *(m_pars[index]);
184 }
185 
186 
187 /***********************************************************************//**
188  * @brief Returns reference to model parameter by name const version)
189  *
190  * @param[in] name Parameter name.
191  * @return Reference to model parameter.
192  *
193  * @exception GException::invalid_argument
194  * Parameter with specified name not found.
195  *
196  * Returns a const reference to the model parameter of the specified
197  * @p name. Throws an exception if no parameter with @p name is found.
198  ***************************************************************************/
199 const GModelPar& GModel::operator[](const std::string& name) const
200 {
201  // Get parameter index
202  int index = 0;
203  for (; index < size(); ++index) {
204  if (m_pars[index]->name() == name) {
205  break;
206  }
207  }
208 
209  // Throw exception if parameter name was not found
210  if (index >= size()) {
211  std::string msg = "Model parameter \""+name+"\" not found in model. "
212  "Please specify a valid model parameter name.";
214  }
215 
216  // Return reference
217  return *(m_pars[index]);
218 }
219 
220 
221 /*==========================================================================
222  = =
223  = Public methods =
224  = =
225  ==========================================================================*/
226 
227 /***********************************************************************//**
228  * @brief Returns reference to model parameter by index
229  *
230  * @param[in] index Parameter index [0,...,size()[.
231  * @return Reference to model parameter.
232  *
233  * @exception GException::out_of_range
234  * Parameter index is out of range.
235  *
236  * Returns a reference to the model parameter of the specified @p index.
237  * Throws an exception if @p index is not valid.
238  ***************************************************************************/
239 GModelPar& GModel::at(const int& index)
240 {
241  // Raise exception if index is out of range
242  if (index < 0 || index >= size()) {
243  throw GException::out_of_range(G_AT, "Parameter index", index, size());
244  }
245 
246  // Return reference
247  return *(m_pars[index]);
248 }
249 
250 
251 /***********************************************************************//**
252  * @brief Returns reference to model parameter by index (const version)
253  *
254  * @param[in] index Parameter index [0,...,size()[.
255  * @return Const reference to model parameter.
256  *
257  * @exception GException::out_of_range
258  * Parameter index is out of range.
259  *
260  * Returns a const reference to the model parameter of the specified
261  * @p index. Throws an exception if @p index is not valid.
262  ***************************************************************************/
263 const GModelPar& GModel::at(const int& index) const
264 {
265  // Raise exception if index is out of range
266  if (index < 0 || index >= size()) {
267  throw GException::out_of_range(G_AT, "Parameter index", index, size());
268  }
269 
270  // Return reference
271  return *(m_pars[index]);
272 }
273 
274 
275 /***********************************************************************//**
276  * @brief Checks if parameter name exists
277  *
278  * @param[in] name Parameter name.
279  * @return True if parameter with specified @p name exists.
280  *
281  * Searches all parameter names for a match with the specified @p name. If
282  * the specified name has been found, true is returned.
283  ***************************************************************************/
284 bool GModel::has_par(const std::string& name) const
285 {
286  // Default found flag to false
287  bool found = false;
288 
289  // Search for parameter name
290  for (int i = 0; i < size(); ++i) {
291  if (m_pars[i]->name() == name) {
292  found = true;
293  break;
294  }
295  }
296 
297  // Return
298  return found;
299 }
300 
301 
302 /***********************************************************************//**
303  * @brief Returns instruments to which model applies
304  *
305  * @return Instruments.
306  *
307  * Returns a comma separated list of instruments to which model applies. If
308  * no instrument exists then an empty string is returned.
309  ***************************************************************************/
310 std::string GModel::instruments(void) const
311 {
312  // Initialise string
313  std::string result;
314 
315  // Attach all instruments
316  for (int i = 0; i < m_instruments.size(); ++i) {
317  if (i > 0) {
318  result += ",";
319  }
320  result += m_instruments[i];
321  }
322 
323  // Return
324  return result;
325 }
326 
327 
328 /***********************************************************************//**
329  * @brief Set instruments to which model applies
330  *
331  * @param[in] instruments String of instruments.
332  *
333  * Sets the instruments to which the model applies from a comma separated
334  * list of strings. The instrument names are case sensitive.
335  *
336  * If the @p instrument string is empty, the model is considered to apply to
337  * all instruments.
338  ***************************************************************************/
339 void GModel::instruments(const std::string& instruments)
340 {
341  // Clear instruments vector
342  m_instruments.clear();
343 
344  // Extract instruments
345  std::vector<std::string> inst = gammalib::split(instruments, ",");
346 
347  // Attach all instruments
348  for (int i = 0; i < inst.size(); ++i) {
349  m_instruments.push_back(gammalib::strip_whitespace(inst[i]));
350  }
351 
352  // Return
353  return;
354 }
355 
356 
357 /***********************************************************************//**
358  * @brief Returns reference to scale parameter by index
359  *
360  * @param[in] index Scale parameter index [0,...,scales()[.
361  * @return Reference to scale parameter.
362  *
363  * @exception GException::out_of_range
364  * Scale parameter index is out of range.
365  *
366  * Returns a reference to the scale parameter of the specified @p index.
367  * Throws an exception if @p index is not valid.
368  ***************************************************************************/
369 GModelPar& GModel::scale(const int& index)
370 {
371  // Raise exception if index is out of range
372  if (index < 0 || index >= scales()) {
373  throw GException::out_of_range(G_SCALE, "Scale parameter index",
374  index, scales());
375  }
376 
377  // Return reference
378  return (m_scales[index]);
379 }
380 
381 
382 /***********************************************************************//**
383  * @brief Returns reference to scale parameter by index (const version)
384  *
385  * @param[in] index Scale parameter index [0,...,scales()[.
386  * @return Reference to scale parameter.
387  *
388  * @exception GException::out_of_range
389  * Scale parameter index is out of range.
390  *
391  * Returns a reference to the scale parameter of the specified @p index.
392  * Throws an exception if @p index is not valid.
393  ***************************************************************************/
394 const GModelPar& GModel::scale(const int& index) const
395 {
396  // Raise exception if index is out of range
397  if (index < 0 || index >= scales()) {
398  throw GException::out_of_range(G_SCALE, "Scale parameter index",
399  index, scales());
400  }
401 
402  // Return reference
403  return (m_scales[index]);
404 }
405 
406 
407 /***********************************************************************//**
408  * @brief Returns model scale factor for a given instrument
409  *
410  * @param[in] instrument Instrument.
411  *
412  * Returns the model scale factor for a given @p instrument. The search is
413  * case sensitive.
414  *
415  * If the @p instrument is not found, the method returns a scale factor of
416  * unity.
417  ***************************************************************************/
418 GModelPar GModel::scale(const std::string& instrument) const
419 {
420  // Initialise unit scale factor
422  scale.value(1.0);
423  scale.name(instrument);
424  scale.fix();
425 
426  // Search for instrument and recover scale factor if the instrument
427  // has been found.
428  for (int i = 0; i < m_scales.size(); ++i) {
429  if (m_scales[i].name() == instrument) {
430  scale = m_scales[i];
431  break;
432  }
433  }
434 
435  // Return scale factor
436  return scale;
437 }
438 
439 
440 /***********************************************************************//**
441  * @brief Set model scale factor for a given instrument
442  *
443  * @param[in] par Model parameter for scaling.
444  *
445  * Sets the model parameter for a given instrument. The instrument name is
446  * case sensitive, but any leading to trailing white space will be stripped.
447  *
448  * If the instrument is not yet defined it will be appended to the list of
449  * instruments.
450  ***************************************************************************/
451 void GModel::scale(const GModelPar& par)
452 {
453  // String leading and trailing while space
454  std::string instrument = gammalib::strip_whitespace(par.name());
455 
456  // Search for instrument and copy the model parameter if the instrument
457  // has been found. Make sure that the instrument name is in upper case.
458  bool found = false;
459  for (int i = 0; i < m_scales.size(); ++i) {
460  if (m_scales[i].name() == instrument) {
461  found = true;
462  m_scales[i] = par;
463  m_scales[i].name(instrument);
464  m_scales[i].has_grad(true);
465  break;
466  }
467  }
468 
469  // If instrument has not been found then append it now to the list
470  // of instruments.
471  if (!found) {
472 
473  // Push scale parameter in list
474  m_scales.push_back(par);
475 
476  // Get index of last scale parameter
477  int i = m_scales.size()-1;
478 
479  // Set instrument name and signal availability of gradient
480  m_scales[i].name(instrument);
481  m_scales[i].has_grad(true);
482 
483  // Push scale parameter on parameter stack
484  m_pars.push_back(&m_scales[i]);
485 
486  } // endif: new scale parameter
487 
488  // Return
489  return;
490 }
491 
492 
493 /***********************************************************************//**
494  * @brief Returns observation identifiers to which model applies
495  *
496  * @return Observation identifiers.
497  *
498  * Returns a comma separated list of observation identifiers to which model
499  * applies. If no observation identifier exists then an empty string is
500  * returned.
501  ***************************************************************************/
502 std::string GModel::ids(void) const
503 {
504  // Initialise string
505  std::string result;
506 
507  // Attach all observation identifiers
508  for (int i = 0; i < m_ids.size(); ++i) {
509  if (i > 0) {
510  result += ",";
511  }
512  result += m_ids[i];
513  }
514 
515  // Return
516  return result;
517 }
518 
519 
520 /***********************************************************************//**
521  * @brief Set observation identifiers to which model applies
522  *
523  * @param[in] ids String of observation identifiers.
524  *
525  * Sets the observation identifiers to which the model applies from a comma
526  * separated list of strings. The observation identifiers are case sensitive,
527  * but any leading and trailing whitespace will be stripped.
528  *
529  * If the observation identifier string is empty, the model is considered to
530  * apply to all observation identifiers.
531  ***************************************************************************/
532 void GModel::ids(const std::string& ids)
533 {
534  // Clear observation identifier vector
535  m_ids.clear();
536 
537  // Extract observation identifiers
538  std::vector<std::string> id = gammalib::split(ids, ",");
539 
540  // Attach all observation identifiers
541  for (int i = 0; i < id.size(); ++i) {
542  m_ids.push_back(gammalib::strip_whitespace(id[i]));
543  }
544 
545  // Return
546  return;
547 }
548 
549 
550 /***********************************************************************//**
551  * @brief Verifies if model is valid for a given instrument and identifier
552  *
553  * @param[in] instrument Instrument name.
554  * @param[in] id Observation identifier.
555  * @return Validity flag.
556  *
557  * Checks if specified instrument name and observation identifier is in list
558  * of applicable instruments and identifiers. The check is case sensitive.
559  *
560  * If the list of applicable instruments is empty, the model applies to all
561  * possible instruments. If the list of applicable observation identifiers
562  * is empty, the model applies to all identifiers.
563  *
564  * If an empty string is provided as @p instrument parameter, the check for
565  * instrument validity will be skipped. Similarily, if an empty string is
566  * provided as @p id parameter, the identifier check will be skipped. This
567  * allows for example to check for models of a given identifier whatever the
568  * instrument, or for models for a given instrument, whatever the identifier.
569  ***************************************************************************/
570 bool GModel::is_valid(const std::string& instrument,
571  const std::string& id) const
572 {
573  // Initialise validity
574  bool valid = true;
575 
576  // Check if model applies to instrument
577  if (!m_instruments.empty() && !instrument.empty()) {
578 
579  // Initialise validity flag
580  valid = false;
581 
582  // Check if instrument is in list
583  for (int i = 0; i < m_instruments.size(); ++i) {
584  if (instrument == m_instruments[i]) {
585  valid = true;
586  break;
587  }
588  }
589 
590  }
591 
592  // Check if model applies to observation identifier
593  if (valid && !m_ids.empty() && !id.empty()) {
594 
595  // Initialise validity flag
596  valid = false;
597 
598  // Check if name is in list
599  for (int i = 0; i < m_ids.size(); ++i) {
600  if (id == m_ids[i]) {
601  valid = true;
602  break;
603  }
604  }
605 
606  }
607 
608  // Return
609  return valid;
610 }
611 
612 
613 /*==========================================================================
614  = =
615  = Private methods =
616  = =
617  ==========================================================================*/
618 
619 /***********************************************************************//**
620  * @brief Initialise class members
621  ***************************************************************************/
623 {
624  // Initialise members
625  m_name.clear();
626  m_instruments.clear();
627  m_scales.clear();
628  m_ids.clear();
629  m_pars.clear();
631  m_ts = 0.0;
632  m_has_ts = false;
633  m_has_tscalc = false;
634  m_tscalc = false;
635  m_has_eval_inx = false;
636  m_eval_inx.clear();
637 
638  // Return
639  return;
640 }
641 
642 
643 /***********************************************************************//**
644  * @brief Copy class members
645  *
646  * @param[in] model Model.
647  ***************************************************************************/
648 void GModel::copy_members(const GModel& model)
649 {
650  // Copy members
651  m_name = model.m_name;
653  m_scales = model.m_scales;
654  m_ids = model.m_ids;
655  m_pars = model.m_pars;
657  m_ts = model.m_ts;
658  m_has_ts = model.m_has_ts;
659  m_has_tscalc = model.m_has_tscalc;
660  m_tscalc = model.m_tscalc;
662  m_eval_inx = model.m_eval_inx;
663 
664  // Return
665  return;
666 }
667 
668 
669 /***********************************************************************//**
670  * @brief Delete class members
671  ***************************************************************************/
673 {
674  // Return
675  return;
676 }
677 
678 
679 /***********************************************************************//**
680  * @brief Read model attributes
681  *
682  * @param[in] xml XML element.
683  ***************************************************************************/
685 {
686  // Set model name
687  name(xml.attribute("name"));
688 
689  // Set instruments
690  instruments(xml.attribute("instrument"));
691 
692  // Set observation identifiers
693  ids(xml.attribute("id"));
694 
695  // Set model TS
696  if (xml.has_attribute("ts")) {
697  std::string ts = xml.attribute("ts");
698  this->ts(gammalib::todouble(ts));
699  }
700 
701  // Set TS computation flag
702  if (xml.has_attribute("tscalc")) {
703  bool tscalc = (xml.attribute("tscalc") == "1") ? true : false;
704  this->tscalc(tscalc);
705  }
706 
707  // Read instrument scales
708  read_scales(xml);
709 
710  // Read model associations
711  m_associations.read(xml);
712 
713  // Return
714  return;
715 }
716 
717 
718 /***********************************************************************//**
719  * @brief Write model attributes
720  *
721  * @param[in] xml XML element.
722  ***************************************************************************/
724 {
725  // Set model name
726  xml.attribute("name", name());
727 
728  // Set model type
729  xml.attribute("type", type());
730 
731  // Set instruments
732  std::string instruments = this->instruments();
733  if (instruments.length() > 0) {
734  xml.attribute("instrument", instruments);
735  }
736 
737  // Set observation identifiers
738  std::string identifiers = ids();
739  if (identifiers.length() > 0) {
740  xml.attribute("id", identifiers);
741  }
742 
743  // If available, set "ts" attribute
744  if (m_has_ts) {
745  xml.attribute("ts", gammalib::str(ts(), 3));
746  }
747 
748  // If available, set "tscalc" attribute
749  if (m_has_tscalc) {
750  std::string ts_calc = tscalc() ? "1" : "0";
751  xml.attribute("tscalc", ts_calc);
752  }
753 
754  // Write instrument scales
755  write_scales(xml);
756 
757  // Write model associations
758  m_associations.write(xml);
759 
760  // Return
761  return;
762 }
763 
764 
765 /***********************************************************************//**
766  * @brief Print model attributes
767  *
768  * @return Returns string with model attributes.
769  ***************************************************************************/
770 std::string GModel::print_attributes(void) const
771 {
772  // Initialise result string
773  std::string result;
774 
775  // Append model name
776  result.append(gammalib::parformat("Name")+name());
777 
778  // Append instruments
779  result.append("\n"+gammalib::parformat("Instruments"));
780  if (!m_instruments.empty()) {
781  for (int i = 0; i < m_instruments.size(); ++i) {
782  if (i > 0) {
783  result.append(", ");
784  }
785  result.append(m_instruments[i]);
786  }
787  }
788  else {
789  result.append("all");
790  }
791 
792  // Append Test Statistic
793  if (m_has_ts) {
794  result.append("\n"+gammalib::parformat("Test Statistic"));
795  result.append(gammalib::str(ts()));
796  }
797  else if (m_tscalc) {
798  result.append("\n"+gammalib::parformat("Test Statistic"));
799  result.append("Computation requested");
800  }
801 
802  // Append observation identifiers
803  result.append("\n"+gammalib::parformat("Observation identifiers"));
804  if (!m_ids.empty()) {
805  for (int i = 0; i < m_ids.size(); ++i) {
806  if (i > 0) {
807  result.append(", ");
808  }
809  result.append(m_ids[i]);
810  }
811  }
812  else {
813  result.append("all");
814  }
815 
816  // Append associations
817  if (!m_associations.is_empty()) {
818  result.append("\n"+gammalib::parformat("Associations"));
819  for (int i = 0; i < m_associations.size(); ++i) {
820  if (i > 0) {
821  result.append(", ");
822  }
823  result.append(m_associations[i].name());
824  }
825  }
826 
827  // Return result
828  return result;
829 }
830 
831 
832 /***********************************************************************//**
833  * @brief Read instrument scales from XML element
834  *
835  * @param[in] xml XML source element.
836  *
837  * Reads the instrument scale factors from a tag with the following format
838  *
839  * <scaling>
840  * <instrument name="LAT" scale="1.0" min="0.1" max="10.0" value="1.0" free="0"/>
841  * <instrument name="CTA" scale="1.0" min="0.1" max="10.0" value="0.5" free="0"/>
842  * </scaling>
843  *
844  * The instrument name is case sensitive, but any leading and trailing white
845  * space will be removed.
846  *
847  * If no scaling tag is found, all instrument scale factors will be cleared.
848  ***************************************************************************/
850 {
851  // Clear any existing scales
852  m_scales.clear();
853 
854  // Continue only if there is a <scaling> tag
855  if (xml.elements("scaling") != 0) {
856 
857  // Get pointer on first instrument scale factors
858  const GXmlElement* scales = xml.element("scaling", 0);
859 
860  // Determine number of scale factors
861  int nscales = scales->elements("instrument");
862 
863  // Read all scale factors
864  for (int i = 0; i < nscales; ++i) {
865  const GXmlElement* par = scales->element("instrument", i);
867  scale.read(*par);
868  scale.name(gammalib::strip_whitespace(par->attribute("name")));
869  scale.has_grad(true);
870  m_scales.push_back(scale);
871  m_pars.push_back(&m_scales[m_scales.size()-1]);
872  }
873 
874  }
875 
876  // Return
877  return;
878 }
879 
880 
881 /***********************************************************************//**
882  * @brief Write instrument scales into XML element
883  *
884  * @param[in] xml XML source element.
885  *
886  * @exception GException::invalid_value
887  * Invalid number of instrument tags found in XML element.
888  *
889  * If there are instrument scale factors then add a tag with the following
890  * format to the XML element:
891  *
892  * <scaling>
893  * <instrument name="LAT" scale="1" min="0.1" max="10" value="1.0" free="0"/>
894  * <instrument name="CTA" scale="1" min="0.1" max="10" value="0.5" free="0"/>
895  * </scaling>
896  ***************************************************************************/
898 {
899  // Continue only is scale factors are present
900  if (!m_scales.empty()) {
901 
902  // Get number of instruments
903  int num = m_scales.size();
904 
905  // Initialise scaling tag
906  GXmlElement* scale = NULL;
907 
908  // If no <scaling> tag exists then add one now with the required
909  // number of instruments ...
910  if (xml.elements("scaling") == 0) {
911  scale = xml.append("scaling");
912  for (int i = 0; i < num; ++i) {
913  scale->append(GXmlElement("instrument"));
914  }
915  }
916 
917  // ... otherwise get first tag
918  else {
919  scale = xml.element("scaling", 0);
920  }
921 
922  // Verify that scaling tag has the required number of instruments
923  if (scale->elements() != num) {
924  std::string msg = "Number of "+gammalib::str(scale->elements())+
925  " scale elements in XML file does not correspond "
926  "to expected number of "+gammalib::str(num)+
927  " elements. Please verify the XML format.";
929  }
930  int npars = scale->elements("instrument");
931  if (npars != num) {
932  std::string msg = "Number of "+gammalib::str(npars)+" \"instrument\" "
933  "scale elements in XML file does not correspond to "
934  "expected number of "+gammalib::str(num)+
935  " elements. Please verify the XML format.";
937  }
938 
939  // Write all instruments
940  for (int i = 0; i < num; ++i) {
941 
942  // Get instrument element
943  GXmlElement* inst = scale->element("instrument", i);
944 
945  // Set instrument name
946  inst->attribute("name", m_scales[i].name());
947 
948  // Write instrument scaling factor
949  m_scales[i].write(*inst);
950 
951  } // endfor: looped over all instruments
952 
953  }
954 
955  // Return
956  return;
957 }
virtual ~GModel(void)
Destructor.
Definition: GModel.cpp:110
Abstract model class.
Definition: GModel.hpp:100
void free_members(void)
Delete class members.
Definition: GModel.cpp:672
int scales(void) const
Return number of scale parameters in model.
Definition: GModel.hpp:247
Abstract model base class interface definition.
const std::string & name(void) const
Return parameter name.
std::string print_attributes(void) const
Print model attributes.
Definition: GModel.cpp:770
int size(void) const
Return number of associations in container.
double m_ts
Test Statistic of the model.
Definition: GModel.hpp:183
XML element node class.
Definition: GXmlElement.hpp:48
#define G_AT
Definition: GModel.cpp:37
GModelAssociations m_associations
Model associations.
Definition: GModel.hpp:179
bool m_has_eval_inx
Definition: GModel.hpp:186
std::vector< std::string > split(const std::string &s, const std::string &sep)
Split string.
Definition: GTools.cpp:983
virtual int elements(void) const
Return number of GXMLElement children of node.
Definition: GXmlNode.cpp:586
void clear(void)
Clear object.
Gammalib tools definition.
std::string ids(void) const
Returns observation identifiers to which model applies.
Definition: GModel.cpp:502
bool m_tscalc
Signals if TS should be computed.
Definition: GModel.hpp:182
#define G_ACCESS
Definition: GModel.cpp:36
std::string strip_whitespace(const std::string &arg)
Strip leading and trailing whitespace from string.
Definition: GTools.cpp:80
bool has_par(const std::string &name) const
Checks if parameter name exists.
Definition: GModel.cpp:284
bool m_has_ts
Signals if TS is available.
Definition: GModel.hpp:180
std::vector< GModelPar > m_scales
Model instrument scale factors.
Definition: GModel.hpp:176
bool m_has_tscalc
Signals if tscalc attribute is available.
Definition: GModel.hpp:181
#define G_SCALE
Definition: GModel.cpp:38
void write(GXmlElement &xml) const
Write models into XML element.
#define G_WRITE_SCALES
Definition: GModel.cpp:39
std::vector< GModelPar * > m_pars
Pointers to all model parameters.
Definition: GModel.hpp:178
int size(void) const
Return number of parameters in model.
Definition: GModel.hpp:233
void init_members(void)
Initialise class members.
Definition: GModel.cpp:622
bool is_valid(const std::string &instruments, const std::string &ids) const
Verifies if model is valid for a given instrument and identifier.
Definition: GModel.cpp:570
Model parameter class.
Definition: GModelPar.hpp:87
std::vector< std::string > m_instruments
Instruments to which model applies.
Definition: GModel.hpp:175
void copy_members(const GModel &model)
Copy class members.
Definition: GModel.cpp:648
bool has_grad(void) const
Signal if parameter gradient is computed analytically.
GModelPar & at(const int &index)
Returns reference to model parameter by index.
Definition: GModel.cpp:239
virtual GModelPar & operator[](const int &index)
Returns reference to model parameter by index.
Definition: GModel.hpp:202
const GXmlAttribute * attribute(const int &index) const
Return attribute.
const std::string & name(void) const
Return parameter name.
Definition: GModel.hpp:261
void fix(void)
Fix a parameter.
bool has_attribute(const std::string &name) const
Check if element has a given attribute.
std::vector< std::string > m_ids
Identifiers to which model applies.
Definition: GModel.hpp:177
std::string instruments(void) const
Returns instruments to which model applies.
Definition: GModel.cpp:310
const double & ts(void) const
Return Test Statistic value.
Definition: GModel.hpp:292
GModelPar & scale(const int &index)
Returns reference to scale parameter by index.
Definition: GModel.cpp:369
void write_attributes(GXmlElement &xml) const
Write model attributes.
Definition: GModel.cpp:723
virtual GXmlElement * element(const int &index)
Return pointer to GXMLElement child.
Definition: GXmlNode.cpp:640
void read(const GXmlElement &xml)
Read model associations from XML document.
bool is_empty(void) const
Signals if there are no associations in container.
std::string m_name
Model name.
Definition: GModel.hpp:174
GModel(void)
Void constructor.
Definition: GModel.cpp:57
void read(const GXmlElement &xml)
Extract parameter attributes from XML element.
Definition: GModelPar.cpp:229
double value(void) const
Return parameter value.
virtual std::string type(void) const =0
Exception handler interface definition.
std::vector< int > m_eval_inx
Definition: GModel.hpp:188
void read_scales(const GXmlElement &xml)
Read instrument scales from XML element.
Definition: GModel.cpp:849
void read_attributes(const GXmlElement &xml)
Read model attributes.
Definition: GModel.cpp:684
virtual GModel & operator=(const GModel &model)
Assignment operator.
Definition: GModel.cpp:132
virtual GXmlNode * append(const GXmlNode &node)
Append XML child node.
Definition: GXmlNode.cpp:287
std::string parformat(const std::string &s, const int &indent=0)
Convert string in parameter format.
Definition: GTools.cpp:1143
void write_scales(GXmlElement &xml) const
Write instrument scales into XML element.
Definition: GModel.cpp:897
const bool & tscalc(void) const
Return Test Statistic computation flag.
Definition: GModel.hpp:326
double todouble(const std::string &arg)
Convert string into double precision value.
Definition: GTools.cpp:926
std::string str(const unsigned short int &value)
Convert unsigned short integer value into string.
Definition: GTools.cpp:489