GammaLib  1.7.0.dev
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
GModels.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  * GModels.cpp - Model container class *
3  * ----------------------------------------------------------------------- *
4  * copyright (C) 2009-2018 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 GModels.cpp
23  * @brief Model container 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 "GFilename.hpp"
34 #include "GModels.hpp"
35 #include "GModel.hpp"
36 #include "GModelRegistry.hpp"
37 #include "GObservation.hpp"
38 #include "GXml.hpp"
39 #include "GXmlElement.hpp"
40 
41 /* __ Method name definitions ____________________________________________ */
42 #define G_ACCESS "GModels::operator[](std::string&)"
43 #define G_AT "GModels::at(int&)"
44 #define G_SET1 "GModels::set(int&, GModel&)"
45 #define G_SET2 "GModels::set(std::string&, GModel&)"
46 #define G_APPEND "GModels::append(GModel&)"
47 #define G_INSERT1 "GModels::insert(int&, GModel&)"
48 #define G_INSERT2 "GModels::insert(std::string&, GModel&)"
49 #define G_REMOVE1 "GModels::remove(int&)"
50 #define G_REMOVE2 "GModels::remove(std::string&)"
51 #define G_EXTEND "GModels::extend(GModels&)"
52 #define G_READ "GModels::read(GXml&)"
53 
54 /* __ Macros _____________________________________________________________ */
55 
56 /* __ Coding definitions _________________________________________________ */
57 
58 /* __ Debug definitions __________________________________________________ */
59 
60 
61 /*==========================================================================
62  = =
63  = Constructors/destructors =
64  = =
65  ==========================================================================*/
66 
67 /***********************************************************************//**
68  * @brief Void constructor
69  ***************************************************************************/
71 {
72  // Initialise members
73  init_members();
74 
75  // Return
76  return;
77 }
78 
79 
80 /***********************************************************************//**
81  * @brief Copy constructor
82  *
83  * @param[in] models Model container.
84  ***************************************************************************/
85 GModels::GModels(const GModels& models)
86 {
87  // Initialise members
88  init_members();
89 
90  // Copy members
91  copy_members(models);
92 
93  // Return
94  return;
95 }
96 
97 
98 /***********************************************************************//**
99  * @brief Load constructor
100  *
101  * @param[in] filename XML filename.
102  *
103  * Constructs model container from an XML file. See the read() method for
104  * more information about the expected structure of the XML file.
105  ***************************************************************************/
106 GModels::GModels(const GFilename& filename)
107 {
108  // Initialise members
109  init_members();
110 
111  // Load XML file
112  load(filename);
113 
114  // Return
115  return;
116 }
117 
118 
119 /***********************************************************************//**
120  * @brief Destructor
121  ***************************************************************************/
123 {
124  // Free members
125  free_members();
126 
127  // Return
128  return;
129 }
130 
131 
132 /*==========================================================================
133  = =
134  = Operators =
135  = =
136  ==========================================================================*/
137 
138 /***********************************************************************//**
139  * @brief Assignment operator
140  *
141  * @param[in] models Model container.
142  * @return Model container.
143  ***************************************************************************/
145 {
146  // Execute only if object is not identical
147  if (this != &models) {
148 
149  // Free members
150  free_members();
151 
152  // Initialise members
153  init_members();
154 
155  // Copy members
156  copy_members(models);
157 
158  } // endif: object was not identical
159 
160  // Return
161  return *this;
162 }
163 
164 
165 /***********************************************************************//**
166  * @brief Return pointer to model
167  *
168  * @param[in] name Model name.
169  *
170  * @exception GException::model_not_found
171  * Model with specified name not found in container.
172  *
173  * Returns a pointer to the model with the specified @p name.
174  ***************************************************************************/
175 GModel* GModels::operator[](const std::string& name)
176 {
177  // Get model index
178  int index = get_index(name);
179 
180  // Throw exception if model name was not found
181  if (index == -1) {
183  }
184 
185  // Return pointer
186  return m_models[index];
187 }
188 
189 
190 /***********************************************************************//**
191  * @brief Return pointer to model (const version)
192  *
193  * @param[in] name Model name.
194  *
195  * @exception GException::model_not_found
196  * Model with specified name not found in container.
197  *
198  * Returns a const pointer to the model with the specified @p name.
199  ***************************************************************************/
200 const GModel* GModels::operator[](const std::string& name) const
201 {
202  // Get model index
203  int index = get_index(name);
204 
205  // Throw exception if model name was not found
206  if (index == -1) {
208  }
209 
210  // Return pointer
211  return m_models[index];
212 }
213 
214 
215 /*==========================================================================
216  = =
217  = Public methods =
218  = =
219  ==========================================================================*/
220 
221 /***********************************************************************//**
222  * @brief Clear object
223  *
224  * Removes all models from the container.
225  ***************************************************************************/
226 void GModels::clear(void)
227 {
228  // Free class members (base and derived classes, derived class first)
229  free_members();
230 
231  // Initialise members
232  init_members();
233 
234  // Return
235  return;
236 }
237 
238 
239 /***********************************************************************//**
240  * @brief Clone instance
241  *
242  * @return Pointer to deep copy of model container
243  *
244  * Makes a deep copy of the model container instance.
245  ***************************************************************************/
247 {
248  return new GModels(*this);
249 }
250 
251 
252 /***********************************************************************//**
253  * @brief Return pointer to model
254  *
255  * @param[in] index Model index [0,...,size()-1].
256  *
257  * @exception GException::out_of_range
258  * Model index is out of range.
259  *
260  * Returns a pointer to the model with the specified @p index.
261  ***************************************************************************/
262 GModel* GModels::at(const int& index)
263 {
264  // Compile option: raise an exception if index is out of range
265  #if defined(G_RANGE_CHECK)
266  if (index < 0 || index >= size()) {
267  throw GException::out_of_range(G_AT, "Model index", index, size());
268  }
269  #endif
270 
271  // Return pointer
272  return m_models[index];
273 }
274 
275 
276 /***********************************************************************//**
277  * @brief Return pointer to model (const version)
278  *
279  * @param[in] index Model index [0,...,size()-1].
280  *
281  * @exception GException::out_of_range
282  * Model index is out of range.
283  *
284  * Returns a const pointer to the model with the specified @p index.
285  ***************************************************************************/
286 const GModel* GModels::at(const int& index) const
287 {
288  // Compile option: raise an exception if index is out of range
289  #if defined(G_RANGE_CHECK)
290  if (index < 0 || index >= size()) {
291  throw GException::out_of_range(G_AT, "Model index", index, size());
292  }
293  #endif
294 
295  // Return pointer
296  return m_models[index];
297 }
298 
299 
300 /***********************************************************************//**
301  * @brief Set model in container
302  *
303  * @param[in] index Model index [0,...,size()-1].
304  * @param[in] model Model.
305  * @return Pointer to deep copy of model.
306  *
307  * @exception GException::out_of_range
308  * Model index is out of range.
309  * @exception GException::invalid_value
310  * Name of model exists already in container.
311  *
312  * Set model in the container. A deep copy of the model will be made.
313  ***************************************************************************/
314 GModel* GModels::set(const int& index, const GModel& model)
315 {
316  // Compile option: raise exception if index is out of range
317  #if defined(G_RANGE_CHECK)
318  if (index < 0 || index >= size()) {
319  throw GException::out_of_range(G_SET1, index, 0, size()-1);
320  }
321  #endif
322 
323  // Check if a model with specified name does not yet exist
324  int inx = get_index(model.name());
325  if (inx != -1 && inx != index) {
326  std::string msg =
327  "Attempt to set model with name \""+model.name()+"\" in model "
328  "container at index "+gammalib::str(index)+", but a model with "
329  "the same name exists already at index "+gammalib::str(inx)+
330  " in the container. Every model in the model container needs a "
331  "unique name.";
332  throw GException::invalid_value(G_SET1, msg);
333  }
334 
335  // Free existing model only if it differs from current model. This
336  // prevents unintential deallocation of the argument
337  if ((m_models[index] != NULL) && (m_models[index] != &model)) {
338  delete m_models[index];
339  }
340 
341  // Assign new model by cloning
342  m_models[index] = model.clone();
343 
344  // Return pointer to model
345  return m_models[index];
346 }
347 
348 
349 /***********************************************************************//**
350  * @brief Set model in container
351  *
352  * @param[in] name Model name.
353  * @param[in] model Model pointer.
354  * @return Pointer to deep copy of model.
355  *
356  * @exception GException::model_not_found
357  * Model with specified name not found in container.
358  * @exception GException::invalid_value
359  * Name of model exists already in container.
360  *
361  * Set model in the container. A deep copy of the model will be made.
362  ***************************************************************************/
363 GModel* GModels::set(const std::string& name, const GModel& model)
364 {
365  // Get parameter index
366  int index = get_index(name);
367 
368  // Throw exception if parameter name was not found
369  if (index == -1) {
370  throw GException::model_not_found(G_SET2, name);
371  }
372 
373  // Check if a model with specified name does not yet exist
374  int inx = get_index(model.name());
375  if (inx != -1 && inx != index) {
376  std::string msg =
377  "Attempt to set model with name \""+model.name()+"\" in model"
378  " container at index "+gammalib::str(index)+", but a model with"
379  " the same name exists already at index "+gammalib::str(inx)+
380  " in the container.\n"
381  "Every model in the model container needs a unique name.";
382  throw GException::invalid_value(G_SET2, msg);
383  }
384 
385  // Free existing model only if it differs from current model. This
386  // prevents unintential deallocation of the argument
387  if ((m_models[index] != NULL) && (m_models[index] != &model)) {
388  delete m_models[index];
389  }
390 
391  // Assign new model by cloning
392  m_models[index] = model.clone();
393 
394  // Return pointer to model
395  return m_models[index];
396 }
397 
398 
399 /***********************************************************************//**
400  * @brief Append model to container
401  *
402  * @param[in] model Model.
403  * @return Pointer to deep copy of model.
404  *
405  * @exception GException::invalid_value
406  * Name of model exists already in container.
407  *
408  * Appends model to the container by making a deep copy of the model and
409  * storing its pointer.
410  ***************************************************************************/
412 {
413  // Check if a model with specified name does not yet exist
414  int inx = get_index(model.name());
415  if (inx != -1) {
416  std::string msg =
417  "Attempt to append model with name \""+model.name()+"\" to model"
418  " container, but a model with the same name exists already at"
419  " index "+gammalib::str(inx)+" in the container."
420  " Every model in the model container needs a unique name.";
422  }
423 
424  // Create deep copy of model
425  GModel* ptr = model.clone();
426 
427  // Append deep copy of model
428  m_models.push_back(ptr);
429 
430  // Return pointer to model
431  return ptr;
432 }
433 
434 
435 /***********************************************************************//**
436  * @brief Insert model into container
437  *
438  * @param[in] index Model index [0,...,size()-1].
439  * @param[in] model Model.
440  * @return Pointer to deep copy of model.
441  *
442  * @exception GException::out_of_range
443  * Model index is out of range.
444  * @exception GException::invalid_value
445  * Name of model exists already in container.
446  *
447  * Inserts a @p model into the container before the model with the specified
448  * @p index.
449  ***************************************************************************/
450 GModel* GModels::insert(const int& index, const GModel& model)
451 {
452  // Compile option: raise exception if index is out of range
453  #if defined(G_RANGE_CHECK)
454  if (is_empty()) {
455  if (index > 0) {
456  throw GException::out_of_range(G_INSERT1, index, 0, size()-1);
457  }
458  }
459  else {
460  if (index < 0 || index >= size()) {
461  throw GException::out_of_range(G_INSERT1, index, 0, size()-1);
462  }
463  }
464  #endif
465 
466  // Check if a model with specified name does not yet exist
467  int inx = get_index(model.name());
468  if (inx != -1) {
469  std::string msg =
470  "Attempt to insert model with name \""+model.name()+"\" in model"
471  " container before index "+gammalib::str(index)+", but a model"
472  " with the same name exists already at index "+gammalib::str(inx)+
473  " in the container.\n"
474  "Every model in the model container needs a unique name.";
476  }
477 
478  // Create deep copy of model
479  GModel* ptr = model.clone();
480 
481  // Inserts deep copy of model
482  m_models.insert(m_models.begin()+index, ptr);
483 
484  // Return pointer to model
485  return ptr;
486 }
487 
488 
489 /***********************************************************************//**
490  * @brief Insert model into container
491  *
492  * @param[in] name Model name.
493  * @param[in] model Model.
494  * @return Pointer to deep copy of model.
495  *
496  * @exception GException::model_not_found
497  * Model with specified name not found in container.
498  * @exception GException::invalid_value
499  * Name of model exists already in container.
500  *
501  * Inserts a @p model into the container before the model with the specified
502  * @p name.
503  ***************************************************************************/
504 GModel* GModels::insert(const std::string& name, const GModel& model)
505 {
506  // Get parameter index
507  int index = get_index(name);
508 
509  // Throw exception if parameter name was not found
510  if (index == -1) {
512  }
513 
514  // Check if a model with specified name does not yet exist
515  int inx = get_index(model.name());
516  if (inx != -1) {
517  std::string msg =
518  "Attempt to insert model with name \""+model.name()+"\" in model"
519  " container before index "+gammalib::str(index)+", but a model"
520  " with the same name exists already at index "+gammalib::str(inx)+
521  " in the container.\n"
522  "Every model in the model container needs a unique name.";
524  }
525 
526  // Create deep copy of model
527  GModel* ptr = model.clone();
528 
529  // Inserts deep copy of model
530  m_models.insert(m_models.begin()+index, ptr);
531 
532  // Return pointer to model
533  return ptr;
534 }
535 
536 
537 /***********************************************************************//**
538  * @brief Remove model from container
539  *
540  * @param[in] index Model index [0,...,size()-1].
541  *
542  * @exception GException::out_of_range
543  * Model index is out of range.
544  *
545  * Remove model of specified @p index from container.
546  ***************************************************************************/
547 void GModels::remove(const int& index)
548 {
549  // Compile option: raise exception if index is out of range
550  #if defined(G_RANGE_CHECK)
551  if (index < 0 || index >= size()) {
552  throw GException::out_of_range(G_REMOVE1, index, 0, size()-1);
553  }
554  #endif
555 
556  // Delete model
557  delete m_models[index];
558 
559  // Erase model component from container
560  m_models.erase(m_models.begin() + index);
561 
562  // Return
563  return;
564 }
565 
566 
567 /***********************************************************************//**
568  * @brief Remove model from container
569  *
570  * @param[in] name Model name.
571  *
572  * @exception GException::model_not_found
573  * Model with specified name not found in container.
574  *
575  * Remove model of specified @p name from container.
576  ***************************************************************************/
577 void GModels::remove(const std::string& name)
578 {
579  // Get parameter index
580  int index = get_index(name);
581 
582  // Throw exception if parameter name was not found
583  if (index == -1) {
585  }
586 
587  // Delete model
588  delete m_models[index];
589 
590  // Erase model component from container
591  m_models.erase(m_models.begin() + index);
592 
593  // Return
594  return;
595 }
596 
597 
598 /***********************************************************************//**
599  * @brief Append model container
600  *
601  * @param[in] models Model container.
602  *
603  * Append model container to the container.
604  ***************************************************************************/
605 void GModels::extend(const GModels& models)
606 {
607  // Do nothing if model container is empty
608  if (!models.is_empty()) {
609 
610  // Get size. Note that we extract the size first to avoid an
611  // endless loop that arises when a container is appended to
612  // itself.
613  int num = models.size();
614 
615  // Reserve enough space
616  reserve(size() + num);
617 
618  // Loop over all model components and append pointers to deep copies
619  for (int i = 0; i < num; ++i) {
620 
621  // Check if model name does not yet exist
622  int inx = get_index(models[i]->name());
623  if (inx != -1) {
624  std::string msg =
625  "Attempt to append model with name \""+models[i]->name()+
626  "\" to model container, but a model with the same name"
627  " exists already at index "+gammalib::str(inx)+" in the"
628  " container.\n"
629  "Every model in the model container needs a unique name.";
631  }
632 
633  // Append model to container
634  m_models.push_back(models[i]->clone());
635 
636  } // endfor: looped over all models
637 
638  } // endif: model container was not empty
639 
640  // Return
641  return;
642 }
643 
644 
645 /***********************************************************************//**
646  * @brief Signals if model name exists
647  *
648  * @param[in] name Model name.
649  * @return True if model with specified @p name exists.
650  *
651  * Searches all model names for a match with the specified @p name. If the
652  * specified name has been found, true is returned.
653  ***************************************************************************/
654 bool GModels::contains(const std::string& name) const
655 {
656  // Get model index
657  int index = get_index(name);
658 
659  // Return
660  return (index != -1);
661 }
662 
663 
664 /***********************************************************************//**
665  * @brief Load models from XML file
666  *
667  * @param[in] filename XML filename.
668  *
669  * Loads all models from an XML file. See the read() method for more
670  * information about the expected structure of the XML file.
671  ***************************************************************************/
672 void GModels::load(const GFilename& filename)
673 {
674  // Clear any existing models
675  clear();
676 
677  // Load XML document
678  GXml xml(filename.url());
679 
680  // Read models from XML document
681  read(xml);
682 
683  // Return
684  return;
685 }
686 
687 
688 /***********************************************************************//**
689  * @brief Save models into XML file
690  *
691  * @param[in] filename XML filename.
692  *
693  * Saves all models in the container into an XML file.
694  ***************************************************************************/
695 void GModels::save(const GFilename& filename) const
696 {
697  // Declare empty XML document
698  GXml xml;
699 
700  // Write models into XML file
701  write(xml);
702 
703  // Save XML document
704  xml.save(filename);
705 
706  // Return
707  return;
708 }
709 
710 
711 /***********************************************************************//**
712  * @brief Read models from XML document
713  *
714  * @param[in] xml XML document.
715  *
716  * @exception GException::model_invalid
717  * Invalid model type encountered.
718  *
719  * Read models from the first source library found in the XML document. The
720  * XML document is expected to have the following structure
721  *
722  * <source_library title="source library">
723  * <source name="Source1" type="PointSource">
724  * ...
725  * </source>
726  * <source name="Source2" type="DiffuseSource">
727  * ...
728  * </source>
729  * </source_library>
730  *
731  * Each @p source tag will be interpreted as a model component.
732  *
733  * @todo Sources names are not verified so far for uniqueness. This would be
734  * required to achieve an unambiguous update of parameters in an already
735  * existing XML file when using the write method.
736  ***************************************************************************/
737 void GModels::read(const GXml& xml)
738 {
739  // Get pointer on source library
740  const GXmlElement* lib = xml.element("source_library", 0);
741 
742  // Loop over all sources
743  int n = lib->elements("source");
744  for (int i = 0; i < n; ++i) {
745 
746  // Get pointer on source
747  const GXmlElement* src = lib->element("source", i);
748 
749  // Get model type
750  std::string type = src->attribute("type");
751 
752  // Get model
753  GModelRegistry registry;
754  GModel* ptr = registry.alloc(type);
755 
756  // If model if valid then read model from XML file
757  if (ptr != NULL) {
758  ptr->read(*src);
759  }
760 
761  // ... otherwise throw an exception
762  else {
763  throw GException::model_invalid(G_READ, type);
764  }
765 
766  // Append model
767  append(*ptr);
768 
769  // Free model (appending clones the model)
770  delete ptr;
771 
772  } // endfor: looped over all sources
773 
774  // Return
775  return;
776 }
777 
778 
779 /***********************************************************************//**
780  * @brief Write models into XML document
781  *
782  * @param[in] xml XML document.
783  *
784  * Write models into the first source library that is found in the XML
785  * document. In case that no source library exists, one is added to the
786  * document.
787  ***************************************************************************/
788 void GModels::write(GXml& xml) const
789 {
790  // If there is no source library then append one
791  if (xml.elements("source_library") == 0) {
792  xml.append(GXmlElement("source_library title=\"source library\""));
793  }
794 
795  // Get pointer on source library
796  GXmlElement* lib = xml.element("source_library", 0);
797 
798  // Write all sources into library
799  for (int i = 0; i < size(); ++i) {
800  m_models[i]->write(*lib);
801  }
802 
803  // Return
804  return;
805 }
806 
807 
808 /***********************************************************************//**
809  * @brief Return number of model parameters in container
810  *
811  * @return Number of model parameters in container.
812  ***************************************************************************/
813 int GModels::npars(void) const
814 {
815  // Initialise number of parameters
816  int npars = 0;
817 
818  // Sum of number of parameters in model
819  for (int i = 0; i < size(); ++i) {
820  npars += m_models[i]->size();
821  }
822 
823  // Return
824  return npars;
825 }
826 
827 
828 /***********************************************************************//**
829  * @brief Return optimizer parameter container
830  *
831  * @return Optimizer parameter container.
832  *
833  * Returns an optimizer parameter container that is built by extracting
834  * all model pointers from the model and attaching them to the parameter
835  * container. The optimizer parameter container will thus contains a flat
836  * array of a model parameters.
837  ***************************************************************************/
839 {
840  // Initialise parameter container
842 
843  // Attach all parameters
844  for (int i = 0; i < size(); ++i) {
845  GModel* model = m_models[i];
846  int npars = model->size();
847  for (int k = 0; k < npars; ++k) {
848  pars.attach(&((*model)[k]));
849  }
850  }
851 
852  // Return
853  return pars;
854 }
855 
856 
857 /***********************************************************************//**
858  * @brief Evaluate sum of all models
859  *
860  * @param[in] event Observed event.
861  * @param[in] obs Observation.
862  * @param[in] gradients Compute gradients?
863  * @return Value of models.
864  *
865  * Evaluates the sum of all models for the specified event and observation.
866  * Only valid models are considered in this evaluation.
867  *
868  * If the @p gradients flag is true the method will also set the parameter
869  * gradients of the model parameters.
870  ***************************************************************************/
871 double GModels::eval(const GEvent& event,
872  const GObservation& obs,
873  const bool& gradients) const
874 {
875  // Initialise function value
876  double value = 0.0;
877 
878  // Evaluate function for all models
879  for (int i = 0; i < size(); ++i) {
880  if (m_models[i]->is_valid(obs.instrument(), obs.id())) {
881  value += m_models[i]->eval(event, obs, gradients);
882  }
883  }
884 
885  // Return
886  return value;
887 }
888 
889 
890 /***********************************************************************//**
891  * @brief Print models
892  *
893  * @param[in] chatter Chattiness (defaults to NORMAL).
894  * @return String containing model container information.
895  *
896  * Prints all models into a string.
897  ***************************************************************************/
898 std::string GModels::print(const GChatter& chatter) const
899 {
900  // Initialise result string
901  std::string result;
902 
903  // Continue only if chatter is not silent
904  if (chatter != SILENT) {
905 
906  // Append header
907  result.append("=== GModels ===");
908 
909  // Append information
910  result.append("\n"+gammalib::parformat("Number of models"));
911  result.append(gammalib::str(size()));
912  result.append("\n"+gammalib::parformat("Number of parameters"));
913  result.append(gammalib::str(npars()));
914 
915  // Append models
916  for (int i = 0; i < size(); ++i) {
917  result.append("\n"+m_models[i]->print(chatter));
918  }
919 
920  } // endif: chatter was not silent
921 
922  // Return result
923  return result;
924 }
925 
926 
927 /*==========================================================================
928  = =
929  = Private methods =
930  = =
931  ==========================================================================*/
932 
933 /***********************************************************************//**
934  * @brief Initialise class members
935  ***************************************************************************/
937 {
938  // Initialise members
939  m_models.clear();
940 
941  // Return
942  return;
943 }
944 
945 
946 /***********************************************************************//**
947  * @brief Copy class members
948  *
949  * @param[in] models Model container.
950  *
951  * Makes a copy of all class members. All models are deep copied, and the
952  * linear pointer array for parameter access through the GOptimizerPars
953  * base class is set.
954  ***************************************************************************/
955 void GModels::copy_members(const GModels& models)
956 {
957  // Copy models
958  m_models.clear();
959  for (int i = 0; i < models.m_models.size(); ++i) {
960  m_models.push_back((models.m_models[i]->clone()));
961  }
962 
963  // Return
964  return;
965 }
966 
967 
968 /***********************************************************************//**
969  * @brief Delete class members
970  *
971  * Deallocates all models. The method loops over the model container and
972  * deallocates the memory that has been allocated before.
973  ***************************************************************************/
975 {
976  // Free models
977  for (int i = 0; i < m_models.size(); ++i) {
978  delete m_models[i];
979  m_models[i] = NULL;
980  }
981 
982  // Return
983  return;
984 }
985 
986 
987 /***********************************************************************//**
988  * @brief Return model index by name
989  *
990  * @param[in] name Model name.
991  * @return Model index (-1 if model name has not been found)
992  *
993  * Returns model index based on the specified @p name. If no model with the
994  * specified @p name is found the method returns -1.
995  ***************************************************************************/
996 int GModels::get_index(const std::string& name) const
997 {
998  // Initialise index
999  int index = -1;
1000 
1001  // Search model with specified name
1002  for (int i = 0; i < size(); ++i) {
1003  if (m_models[i]->name() == name) {
1004  index = i;
1005  break;
1006  }
1007  }
1008 
1009  // Return index
1010  return index;
1011 }
#define G_APPEND
Definition: GModels.cpp:46
double eval(const GEvent &event, const GObservation &obs, const bool &gradients=false) const
Evaluate sum of all models.
Definition: GModels.cpp:871
Abstract model class.
Definition: GModel.hpp:97
void copy_members(const GModels &models)
Copy class members.
Definition: GModels.cpp:955
Abstract model base class interface definition.
XML element node class interface definition.
void save(const GFilename &filename) const
Save XML document into file.
Definition: GXml.cpp:576
Interface definition for the model registry class.
virtual std::string instrument(void) const =0
void remove(const int &index)
Remove model from container.
Definition: GModels.cpp:547
Model container class definition.
#define G_SET1
Definition: GModels.cpp:44
void read(const GXml &xml)
Read models from XML document.
Definition: GModels.cpp:737
XML class interface definition.
GModels * clone(void) const
Clone instance.
Definition: GModels.cpp:246
GModels(void)
Void constructor.
Definition: GModels.cpp:70
GModel * operator[](const int &index)
Return pointer to model.
Definition: GModels.hpp:227
Optimizer parameter container class.
Abstract interface for the event classes.
Definition: GEvent.hpp:71
void extend(const GModels &models)
Append model container.
Definition: GModels.cpp:605
XML element node class.
Definition: GXmlElement.hpp:47
GOptimizerPars pars(void) const
Return optimizer parameter container.
Definition: GModels.cpp:838
void save(const GFilename &filename) const
Save models into XML file.
Definition: GModels.cpp:695
virtual int elements(void) const
Return number of GXMLElement children of node.
Definition: GXmlNode.cpp:580
Gammalib tools definition.
#define G_INSERT2
Definition: GModels.cpp:48
void reserve(const int &num)
Reserves space for models in container.
Definition: GModels.hpp:283
#define G_REMOVE1
Definition: GModels.cpp:49
void id(const std::string &id)
Set observation identifier.
GModel * insert(const int &index, const GModel &model)
Insert model into container.
Definition: GModels.cpp:450
int size(void) const
Return number of parameters in model.
Definition: GModel.hpp:217
void clear(void)
Clear object.
Definition: GModels.cpp:226
#define G_READ
Definition: GModels.cpp:52
std::vector< GModel * > m_models
List of models.
Definition: GModels.hpp:203
int get_index(const std::string &name) const
Return model index by name.
Definition: GModels.cpp:996
virtual void read(const GXmlElement &xml)=0
Model container class.
Definition: GModels.hpp:150
GXmlElement * element(const int &index)
Return pointer to child element.
Definition: GXml.cpp:419
int elements(void) const
Return number of child elements in XML document root.
Definition: GXml.cpp:384
void free_members(void)
Delete class members.
Definition: GModels.cpp:974
#define G_REMOVE2
Definition: GModels.cpp:50
const GXmlAttribute * attribute(const int &index) const
Return attribute.
const std::string & name(void) const
Return parameter name.
Definition: GModel.hpp:245
XML class.
Definition: GXml.hpp:172
Filename class.
Definition: GFilename.hpp:62
#define G_EXTEND
Definition: GModels.cpp:51
GModel * set(const int &index, const GModel &model)
Set model in container.
Definition: GModels.cpp:314
#define G_SET2
Definition: GModels.cpp:45
GChatter
Definition: GTypemaps.hpp:33
void attach(GOptimizerPar *par)
Attach parameter to container.
Abstract observation base class.
Abstract observation base class interface definition.
GModel * alloc(const std::string &name) const
Allocate model of given name.
virtual GModel * clone(void) const =0
Clones object.
std::string url(void) const
Return Uniform Resource Locator (URL)
Definition: GFilename.hpp:189
virtual GXmlElement * element(const int &index)
Return pointer to GXMLElement child.
Definition: GXmlNode.cpp:634
void write(GXml &xml) const
Write models into XML document.
Definition: GModels.cpp:788
GModel * at(const int &index)
Return pointer to model.
Definition: GModels.cpp:262
void load(const GFilename &filename)
Load models from XML file.
Definition: GModels.cpp:672
bool contains(const std::string &name) const
Signals if model name exists.
Definition: GModels.cpp:654
std::string print(const GChatter &chatter=NORMAL) const
Print models.
Definition: GModels.cpp:898
void init_members(void)
Initialise class members.
Definition: GModels.cpp:936
#define G_ACCESS
Definition: GModels.cpp:42
Exception handler interface definition.
int npars(void) const
Return number of model parameters in container.
Definition: GModels.cpp:813
virtual ~GModels(void)
Destructor.
Definition: GModels.cpp:122
#define G_AT
Definition: GModels.cpp:43
Model registry class definition.
std::string parformat(const std::string &s, const int &indent=0)
Convert string in parameter format.
Definition: GTools.cpp:1022
#define G_INSERT1
Definition: GModels.cpp:47
GModels & operator=(const GModels &models)
Assignment operator.
Definition: GModels.cpp:144
int size(void) const
Return number of models in container.
Definition: GModels.hpp:255
GModel * append(const GModel &model)
Append model to container.
Definition: GModels.cpp:411
Filename class interface definition.
GXmlNode * append(const GXmlNode &node)
Append child node to XML document root.
Definition: GXml.cpp:279
bool is_empty(void) const
Signals if there are no models in container.
Definition: GModels.hpp:269
std::string str(const unsigned short int &value)
Convert unsigned short integer value into string.
Definition: GTools.cpp:413