Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-07-03 08:34:16

0001 //==========================================================================
0002 //  AIDA Detector description implementation 
0003 //--------------------------------------------------------------------------
0004 // Copyright (C) Organisation europeenne pour la Recherche nucleaire (CERN)
0005 // All rights reserved.
0006 //
0007 // For the licensing terms see $DD4hepINSTALL/LICENSE.
0008 // For the list of contributors see $DD4hepINSTALL/doc/CREDITS.
0009 //
0010 // Author     : M.Frank
0011 //
0012 //==========================================================================
0013 #ifndef DD4HEP_COMPONENTPROPERTIES_H
0014 #define DD4HEP_COMPONENTPROPERTIES_H
0015 
0016 // Framework include files
0017 #include <DD4hep/Grammar.h>
0018 
0019 // C/C++ include files
0020 #include <algorithm>
0021 #include <typeinfo>
0022 #include <string>
0023 #include <map>
0024 
0025 /// Namespace for the AIDA detector description toolkit
0026 namespace dd4hep {
0027 
0028   class Property;
0029   class BasicGrammar;
0030 
0031   /// The property class to assign options to actions.
0032   /**
0033    *   Standard implementation of a property mechanism.
0034    *   The data conversion mechanism between various properties
0035    *   uses internally boost::spirit to allow also conversions
0036    *   between types, which are initially unrelated such as
0037    *   e.g. vector<int> and list<short>.
0038    *
0039    *  Note: This class cannot be saved to a ROOT file!
0040    *
0041    *  \author  M.Frank
0042    *  \version 1.0
0043    *  \ingroup DD4HEP_CORE
0044    */
0045   class Property {
0046   protected:
0047     /// Pointer to the data location
0048     void* m_par                { nullptr };
0049     /// Reference to the grammar of this property (extended type description)
0050     const BasicGrammar* m_hdl  { nullptr };
0051 
0052   public:
0053     /// Default constructor
0054     Property() = default;
0055     /// Copy constructor
0056     Property(const Property& p) = default;
0057     /// User constructor
0058     template <typename TYPE> Property(TYPE& val);
0059     /// Property type name
0060     static std::string type(const Property& proptery);
0061     /// Property type name
0062     static std::string type(const std::type_info& proptery);
0063     /// Access void data pointer
0064     void* ptr() const {      return m_par;    }
0065     /// Property type name
0066     std::string type() const;
0067     /// Access grammar object
0068     const BasicGrammar& grammar() const;
0069     /// Conversion to string value
0070     std::string str() const;
0071     /// Conversion from string value
0072     Property& str(const std::string& input);
0073     /// Conversion from string value
0074     const Property& str(const std::string& input)  const;
0075     /// Assignment operator
0076     Property& operator=(const Property& p) = default;
0077     /// Assignment operator / set new balue
0078     Property& operator=(const char* val);
0079     /// Assignment operator / set new balue
0080     //Property& operator=(const std::string& val);
0081     /// Assignment operator / set new balue
0082     template <typename TYPE> Property& operator=(const TYPE& val);
0083     /// Retrieve value
0084     template <typename TYPE> TYPE value() const;
0085     /// Retrieve value from stack (large values e.g. vectors etc.)
0086     template <typename TYPE> void value(TYPE& value) const;
0087     /// Set value of this property
0088     template <typename TYPE> void set(const TYPE& value);
0089   };
0090 
0091   /// User constructor
0092   template <typename TYPE> Property::Property(TYPE& val)
0093     : m_par(&val), m_hdl(0)
0094     {
0095       m_hdl = &BasicGrammar::get(typeid(TYPE));
0096     }
0097 
0098   /// Set value of this property
0099   template <typename TYPE> void Property::set(const TYPE& val) {
0100     const auto& grm = grammar();
0101     if (grm.type() == typeid(TYPE))
0102       *(TYPE*) m_par = val;
0103     else if (!grm.fromString(m_par, BasicGrammar::instance< TYPE >().str(&val)))
0104       BasicGrammar::invalidConversion(typeid(TYPE), grm.type());
0105   }
0106 
0107   /// Assignment operator / set new balue
0108   template <typename TYPE> Property& Property::operator=(const TYPE& val) {
0109     this->set(val);
0110     return *this;
0111   }
0112 
0113   /// Retrieve value from stack (large values e.g. vectors etc.)
0114   template <typename TYPE> void Property::value(TYPE& val) const {
0115     const auto& grm = grammar();
0116     if (grm.type() == typeid(TYPE))
0117       val = *(TYPE*) m_par;
0118     else if (!BasicGrammar::instance< TYPE >().fromString(&val, this->str()))
0119       BasicGrammar::invalidConversion(grm.type(), typeid(TYPE));
0120   }
0121 
0122   /// Retrieve value
0123   template <typename TYPE> TYPE Property::value() const {
0124     TYPE temp;
0125     this->value(temp);
0126     return temp;
0127   }
0128 
0129   /// Concrete template instantiation of a combined property value pair.
0130   /**
0131    *  Note: This class cannot be saved to a ROOT file!
0132    *
0133    *  \author  M.Frank
0134    *  \version 1.0
0135    *  \ingroup DD4HEP_CORE
0136    */
0137   template <class TYPE> class PropertyValue : private Property {
0138   public:
0139     TYPE data  {};
0140     /// Default constructor
0141     PropertyValue() : Property(data) {}
0142     /// Copy constructor
0143     PropertyValue(const PropertyValue& c) = default;
0144     /// Assignment operator
0145     PropertyValue& operator=(const PropertyValue& c) = default;
0146     /// Assignment operator
0147     PropertyValue& operator=(const TYPE& val) { data = val; return *this;      }
0148     /// Equality operator
0149     bool operator==(const TYPE& val) const { return val == data;               }
0150     /// Access grammar object
0151     const BasicGrammar& grammar() const    { return this->Property::grammar(); }
0152     /// Conversion to string value
0153     std::string str() const                { return this->Property::str();     }
0154     /// Retrieve value with data conversion
0155     template <typename T> T value() const  { return this->Property::value<T>();}
0156     /// Retrieve value from stack with data conversion (large values e.g. vectors etc.)
0157     template <typename T>
0158     void value(TYPE& val) const            { this->Property::value(val);       }
0159     /// Set value of this property with data conversion
0160     template <typename T> void set(const T& val)  { this->Property::set(val);  }
0161   };
0162 
0163   /// Manager to ease the handling of groups of properties.
0164   /**
0165    *  Note: This class cannot be saved to a ROOT file!
0166    *
0167    *  \author  M.Frank
0168    *  \version 1.0
0169    *  \ingroup DD4HEP_CORE
0170    */
0171   class PropertyManager {
0172   public:
0173     /// Property array definition
0174     typedef std::map<std::string, Property> Properties;
0175   protected:
0176     /// Property array/map
0177     Properties m_properties;
0178 
0179     /// Verify that this property does not exist (throw exception if the name was found)
0180     void verifyNonExistence(const std::string& name) const;
0181     /// Verify that this property exists (throw exception if the name was not found)
0182     Properties::iterator verifyExistence(const std::string& name);
0183     /// Verify that this property exists (throw exception if the name was not found)
0184     Properties::const_iterator verifyExistence(const std::string& name) const;
0185 
0186   public:
0187     /// Default constructor
0188     PropertyManager();
0189     /// Default destructor
0190     virtual ~PropertyManager();
0191     /// Access total number of properties
0192     size_t size()  const;
0193     /// Check for existence
0194     bool exists(const std::string& name) const;
0195     /// Access to the property container
0196     Properties& properties()  {  return m_properties;  }
0197     /// Access to the property container
0198     const Properties& properties()  const  {  return m_properties;  }
0199     /// Access property by name (CONST)
0200     const Property& property(const std::string& name) const;
0201     /// Access property by name
0202     Property& property(const std::string& name);
0203     /// Access property by name
0204     Property& operator[](const std::string& name);
0205     /// Access property by name
0206     const Property& operator[](const std::string& name) const;
0207     /// Add a new property
0208     void add(const std::string& name, const Property& property);
0209     /// Add a new property
0210     template <typename T> void add(const std::string& name, T& value)   {
0211       add(name, Property(value));
0212     }
0213     /// Apply functor on properties
0214     template <typename FUNCTOR> void for_each(FUNCTOR& func)   {
0215       std::for_each(m_properties.begin(), m_properties.end(), func);
0216     }
0217     /// Apply functor on properties
0218     template <typename FUNCTOR> void for_each(const FUNCTOR& func)   {
0219       std::for_each(m_properties.begin(), m_properties.end(), func);
0220     }
0221     /// Import properties of another instance
0222     void adopt(const PropertyManager& copy);
0223     /// Dump string values
0224     void dump() const;
0225   };
0226 
0227   /// Property object as base class for all objects supporting properties
0228   /** 
0229    *  Note: This class cannot be saved to a ROOT file!
0230    *
0231    *  \author  M.Frank
0232    *  \version 1.0
0233    */
0234   class PropertyInterface  {
0235   public:
0236     /// Default destructor
0237     virtual ~PropertyInterface() = default;
0238     /// Access to the properties of the object
0239     virtual PropertyManager& properties() = 0;
0240     /// Access to the properties of the object
0241     virtual const PropertyManager& properties() const = 0;
0242     /// Check property for existence
0243     virtual bool hasProperty(const std::string& name) const = 0;
0244     /// Access single property
0245     virtual Property& property(const std::string& name) = 0;
0246   };
0247   
0248   /// Property object as base class for all objects supporting properties
0249   /** 
0250    *  Note: This class cannot be saved to a ROOT file!
0251    *
0252    *  \author  M.Frank
0253    *  \version 1.0
0254    */
0255   class PropertyConfigurable : virtual public PropertyInterface {
0256   protected:
0257     /// Property pool
0258     PropertyManager m_properties;
0259 
0260   public:
0261     /// Standard constructor
0262     PropertyConfigurable();
0263     /// Default destructor
0264     virtual ~PropertyConfigurable();
0265     /// Access to the properties of the object
0266     virtual PropertyManager& properties() override {
0267       return m_properties;
0268     }
0269     /// Access to the properties of the object
0270     virtual const PropertyManager& properties() const override {
0271       return m_properties;
0272     }
0273     /// Check property for existence
0274     virtual bool hasProperty(const std::string& name) const override;
0275     /// Access single property
0276     virtual Property& property(const std::string& name) override;
0277     /// Declare property
0278     template <typename T> void declareProperty(const std::string& nam, T& val);
0279     /// Declare property
0280     template <typename T> void declareProperty(const char* nam, T& val);
0281   };
0282 
0283   /// Declare property
0284   template <typename T> 
0285   void PropertyConfigurable::declareProperty(const std::string& nam, T& val) {
0286     m_properties.add(nam, val);
0287   }
0288 
0289   /// Declare property
0290   template <typename T> 
0291   void PropertyConfigurable::declareProperty(const char* nam, T& val) {
0292     m_properties.add(nam, val);
0293   }
0294 
0295 }      // End namespace dd4hep
0296 #endif // DD4HEP_COMPONENTPROPERTIES_H