LCOV - code coverage report
Current view: top level - src/utils/xml - SUMOSAXAttributes.h (source / functions) Hit Total Coverage
Test: lcov.info Lines: 38 38 100.0 %
Date: 2024-05-06 15:32:35 Functions: 26 28 92.9 %

          Line data    Source code
       1             : /****************************************************************************/
       2             : // Eclipse SUMO, Simulation of Urban MObility; see https://eclipse.dev/sumo
       3             : // Copyright (C) 2007-2024 German Aerospace Center (DLR) and others.
       4             : // This program and the accompanying materials are made available under the
       5             : // terms of the Eclipse Public License 2.0 which is available at
       6             : // https://www.eclipse.org/legal/epl-2.0/
       7             : // This Source Code may also be made available under the following Secondary
       8             : // Licenses when the conditions for such availability set forth in the Eclipse
       9             : // Public License 2.0 are satisfied: GNU General Public License, version 2
      10             : // or later which is available at
      11             : // https://www.gnu.org/licenses/old-licenses/gpl-2.0-standalone.html
      12             : // SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-or-later
      13             : /****************************************************************************/
      14             : /// @file    SUMOSAXAttributes.h
      15             : /// @author  Daniel Krajzewicz
      16             : /// @author  Jakob Erdmann
      17             : /// @author  Michael Behrisch
      18             : /// @date    Fri, 30 Mar 2007
      19             : ///
      20             : // Encapsulated SAX-Attributes
      21             : /****************************************************************************/
      22             : #pragma once
      23             : #include <config.h>
      24             : 
      25             : #include <string>
      26             : #include <vector>
      27             : #include <set>
      28             : 
      29             : #include <utils/common/StringUtils.h>
      30             : #include <utils/common/SUMOTime.h>
      31             : #include <utils/common/ToString.h>
      32             : #include <utils/common/UtilExceptions.h>
      33             : #include "SUMOXMLDefinitions.h"
      34             : 
      35             : 
      36             : // ===========================================================================
      37             : // class declarations
      38             : // ===========================================================================
      39             : class Position;
      40             : class PositionVector;
      41             : class Boundary;
      42             : class RGBColor;
      43             : 
      44             : 
      45             : // ===========================================================================
      46             : // class definitions
      47             : // ===========================================================================
      48             : /**
      49             :  * @class SUMOSAXAttributes
      50             :  * @brief Encapsulated SAX-Attributes
      51             :  *
      52             :  * This class is an interface for using encapsulated SAX-attributes.
      53             :  * Encapsulation is done to allow a common access without the need to
      54             :  *  import all the Xerces-definitions.
      55             :  */
      56             : class SUMOSAXAttributes {
      57             : public:
      58             :     /* @brief Constructor
      59             :      * @param[in] tagName The name of the parsed object type; used for error message generation
      60             :      */
      61             :     SUMOSAXAttributes(const std::string& objectType);
      62             : 
      63             : 
      64             :     /// @brief Destructor
      65    16588387 :     virtual ~SUMOSAXAttributes() { }
      66             : 
      67             : 
      68             :     /** @brief Tries to read given attribute assuming it is an int
      69             :      *
      70             :      * If an error occurs (the attribute is not there, it is not numeric), "ok" is
      71             :      *  set to false. If report is true an error message is written to MsgHandler::getErrorInstance.
      72             :      *
      73             :      * If the value could be read, "ok" is not changed, and the value is returned.
      74             :      *
      75             :      * @param[in] attr The id of the attribute to read
      76             :      * @param[in] objectid The name of the parsed object; used for error message generation
      77             :      * @param[out] ok Whether the value could be read
      78             :      * @param[in] report Whether errors shall be written to msg handler's error instance
      79             :      * @return The read value if given and correct; -1 if an error occurred
      80             :      */
      81             :     template <typename T>
      82             :     T get(int attr, const char* objectid, bool& ok, bool report = true) const;
      83             : 
      84             : 
      85             :     /** @brief Tries to read given attribute assuming it is an int
      86             :      *
      87             :      * If the attribute is not existing in the current element, the default value is returned.
      88             :      * If an error occurs on parsing (the attribute is empty, it is not numeric), "ok" is
      89             :      *  set to false. If report is true an error message is written to MsgHandler::getErrorInstance.
      90             :      *
      91             :      * If the value could be read, "ok" is not changed, and the value is returned.
      92             :      *
      93             :      * @param[in] attr The id of the attribute to read
      94             :      * @param[in] objectid The name of the parsed object; used for error message generation
      95             :      * @param[out] ok Whether the value could be read
      96             :      * @param[in] defaultValue The value to return if the attribute is not within the element
      97             :      * @param[in] report Whether errors shall be written to msg handler's error instance
      98             :      * @return The read value if given and correct; the default value if the attribute does not exist;  -1 if an error occurred
      99             :      */
     100             :     template <typename T>
     101             :     T getOpt(int attr, const char* objectid, bool& ok, T defaultValue = T(), bool report = true) const;
     102             : 
     103             : 
     104             :     /** @brief Tries to read given attribute assuming it is a SUMOTime
     105             :      *
     106             :      * If an error occurs (the attribute is not there, it is not numeric), "ok" is
     107             :      *  set to false and an error message is written to MsgHandler::getErrorInstance.
     108             :      *
     109             :      * Otherwise, "ok" is not changed.
     110             :      *
     111             :      * In dependence to the used time representation, either get<int> or get<double>
     112             :      *  is used.
     113             :      *
     114             :      * @param[in] attr The id of the attribute to read
     115             :      * @param[in] objectid The name of the parsed object; used for error message generation
     116             :      * @param[out] ok Whether the value could be read
     117             :      * @param[in] report Whether errors shall be written to msg handler's error instance
     118             :      * @return The read value if given and correct; -1 if an error occurred
     119             :      */
     120             :     SUMOTime getSUMOTimeReporting(int attr, const char* objectid, bool& ok,
     121             :                                   bool report = true) const;
     122             : 
     123             : 
     124             :     /** @brief Tries to read the SUMOTime 'period' attribute
     125             :      *
     126             :      * If 'period' cannot be found, tries 'freq' as an alias.
     127             :      *
     128             :      * If an error occurs (the attribute is not there, it is not numeric), "ok" is
     129             :      *  set to false and an error message is written to MsgHandler::getErrorInstance.
     130             :      *
     131             :      * Otherwise, "ok" is not changed.
     132             :      *
     133             :      * In dependence to the used time representation, either get<int> or get<double>
     134             :      *  is used.
     135             :      *
     136             :      * @param[in] objectid The name of the parsed object; used for error message generation
     137             :      * @param[out] ok Whether the value could be read
     138             :      * @param[in] report Whether errors shall be written to msg handler's error instance
     139             :      * @return The read value if given and correct; -1 if an error occurred
     140             :      */
     141             :     SUMOTime getPeriod(const char* objectid, bool& ok, bool report = true) const;
     142             : 
     143             : 
     144             :     /** @brief Tries to read given attribute assuming it is a SUMOTime
     145             :      *
     146             :      * If the attribute is not existing in the current element, the default value is returned.
     147             :      * If an error occurs on parsing (the attribute is empty, it is not numeric), "ok" is
     148             :      *  set to false. If report is true an error message is written to MsgHandler::getErrorInstance.
     149             :      *
     150             :      * Otherwise, "ok" is not changed.
     151             :      *
     152             :      * In dependence to the used time representation, either get<int> or get<double>
     153             :      *  is used.
     154             :      *
     155             :      * @param[in] attr The id of the attribute to read
     156             :      * @param[in] objectid The name of the parsed object; used for error message generation
     157             :      * @param[out] ok Whether the value could be read
     158             :      * @param[in] defaultValue The value to return if the attribute is not within the element
     159             :      * @param[in] report Whether errors shall be written to msg handler's error instance
     160             :      * @return The read value if given and correct; the default value if the attribute does not exist;  -1 if an error occurred
     161             :      */
     162             :     SUMOTime getOptSUMOTimeReporting(int attr, const char* objectid, bool& ok,
     163             :                                      SUMOTime defaultValue, bool report = true) const;
     164             : 
     165             : 
     166             :     /** @brief Tries to read the SUMOTime 'period' attribute
     167             :      *
     168             :      * If 'period' cannot be found, tries 'freq' as an alias.
     169             :      *
     170             :      * If both attributes do not exist in the current element, the default value is returned.
     171             :      * If an error occurs on parsing (the attribute is empty, it is not numeric), "ok" is
     172             :      *  set to false. If report is true an error message is written to MsgHandler::getErrorInstance.
     173             :      *
     174             :      * Otherwise, "ok" is not changed.
     175             :      *
     176             :      * In dependence to the used time representation, either get<int> or get<double>
     177             :      *  is used.
     178             :      *
     179             :      * @param[in] objectid The name of the parsed object; used for error message generation
     180             :      * @param[out] ok Whether the value could be read
     181             :      * @param[in] defaultValue The value to return if the attribute is not within the element
     182             :      * @param[in] report Whether errors shall be written to msg handler's error instance
     183             :      * @return The read value if given and correct; the default value if the attribute does not exist;  -1 if an error occurred
     184             :      */
     185             :     SUMOTime getOptPeriod(const char* objectid, bool& ok, SUMOTime defaultValue, bool report = true) const;
     186             : 
     187             : 
     188             : 
     189             :     /// @name virtual methods for retrieving attribute values
     190             :     /// @{
     191             : 
     192             :     /** @brief Returns the information whether the named (by its enum-value) attribute is within the current list
     193             :      *
     194             :      * @param[in] id The id of the attribute to search for
     195             :      * @return Whether the attribute is within the attributes
     196             :      */
     197             :     virtual bool hasAttribute(int id) const = 0;
     198             : 
     199             : 
     200             :     /** @brief Returns the information whether the named attribute is within the current list
     201             :      *
     202             :      * @param[in] id The name of the attribute to search for
     203             :      * @return Whether the named attribute is within the attributes
     204             :      */
     205             :     virtual bool hasAttribute(const std::string& id) const = 0;
     206             : 
     207             : 
     208             :     /**
     209             :      * @brief Returns the bool-value of the named (by its enum-value) attribute
     210             :      *
     211             :      * Tries to retrieve the attribute from the the attribute list. The retrieved
     212             :      *  attribute  (which may be 0) is then parsed using TplConvert<XMLCh>::_2bool.
     213             :      *  If the attribute is empty or ==0, TplConvert<XMLCh>::_2bool throws an
     214             :      *  EmptyData-exception which is passed.
     215             :      * If the value can not be parsed to a bool, TplConvert<XMLCh>::_2bool throws a
     216             :      *  BoolFormatException-exception which is passed.
     217             :      *
     218             :      * @param[in] id The id of the attribute to return the value of
     219             :      * @return The attribute's value as a bool, if it could be read and parsed
     220             :      * @exception EmptyData If the attribute is not known or the attribute value is an empty string
     221             :      * @exception BoolFormatException If the attribute value can not be parsed to a bool
     222             :      */
     223             :     inline bool getBool(int id) const {
     224             :         return StringUtils::toBool(getString(id));
     225             :     }
     226             : 
     227             :     /**
     228             :      * @brief Returns the int-value of the named (by its enum-value) attribute
     229             :      *
     230             :      * Tries to retrieve the attribute from the the attribute list. The retrieved
     231             :      *  attribute  (which may be 0) is then parsed using TplConvert<XMLCh>::_2int.
     232             :      *  If the attribute is empty or ==0, TplConvert<XMLCh>::_2int throws an
     233             :      *  EmptyData-exception which is passed.
     234             :      * If the value can not be parsed to an int, TplConvert<XMLCh>::_2int throws a
     235             :      *  NumberFormatException-exception which is passed.
     236             :      *
     237             :      * @param[in] id The id of the attribute to return the value of
     238             :      * @return The attribute's value as an int, if it could be read and parsed
     239             :      * @exception EmptyData If the attribute is not known or the attribute value is an empty string
     240             :      * @exception NumberFormatException If the attribute value can not be parsed to an int
     241             :      */
     242        2549 :     inline int getInt(int id) const {
     243        5098 :         return StringUtils::toInt(getString(id));
     244             :     }
     245             : 
     246             : 
     247             :     /**
     248             :      * @brief Returns the long-value of the named (by its enum-value) attribute
     249             :      *
     250             :      * Tries to retrieve the attribute from the the attribute list. The retrieved
     251             :      *  attribute  (which may be 0) is then parsed using TplConvert<XMLCh>::_2long.
     252             :      *  If the attribute is empty or ==0, TplConvert<XMLCh>::_2long throws an
     253             :      *  EmptyData-exception which is passed.
     254             :      * If the value can not be parsed to a long, TplConvert<XMLCh>::_2long throws a
     255             :      *  NumberFormatException-exception which is passed.
     256             :      *
     257             :      * @param[in] id The id of the attribute to return the value of
     258             :      * @return The attribute's value as an int, if it could be read and parsed
     259             :      * @exception EmptyData If the attribute is not known or the attribute value is an empty string
     260             :      * @exception NumberFormatException If the attribute value can not be parsed to an int
     261             :      */
     262          10 :     virtual long long int getLong(int id) const {
     263          20 :         return StringUtils::toLong(getString(id));
     264             :     }
     265             : 
     266             : 
     267             :     /**
     268             :      * @brief Returns the string-value of the named (by its enum-value) attribute
     269             :      *
     270             :      * Tries to retrieve the attribute from the the attribute list. The retrieved
     271             :      *  attribute  (which may be 0) is then parsed using TplConvert<XMLCh>::_2str.
     272             :      *  If the attribute is ==0, TplConvert<XMLCh>::_2str throws an
     273             :      *  EmptyData-exception which is passed.
     274             :      *
     275             :      * @param[in] id The id of the attribute to return the value of
     276             :      * @return The attribute's value as a string, if it could be read and parsed
     277             :      * @exception EmptyData If the attribute is not known or the attribute value is an empty string
     278             :      */
     279             :     virtual std::string getString(int id, bool* isPresent = nullptr) const = 0;
     280             : 
     281             : 
     282             :     /**
     283             :      * @brief Returns the string-value of the named (by its enum-value) attribute
     284             :      *
     285             :      * Tries to retrieve the attribute from the the attribute list. The retrieved
     286             :      *  attribute  (which may be 0) is then parsed using TplConvert<XMLCh>::_2strSec.
     287             :      *  If the attribute is ==0, TplConvert<XMLCh>::_2strSec returns the default value.
     288             :      *
     289             :      * @param[in] id The id of the attribute to return the value of
     290             :      * @param[in] def The default value to return if the attribute is not in attributes
     291             :      * @return The attribute's value as a string, if it could be read and parsed
     292             :      * @exception EmptyData If the attribute is not known or the attribute value is an empty string
     293             :      */
     294             :     virtual std::string getStringSecure(int id, const std::string& def) const = 0;
     295             : 
     296             : 
     297             :     /**
     298             :      * @brief Returns the double-value of the named (by its enum-value) attribute
     299             :      *
     300             :      * Tries to retrieve the attribute from the the attribute list. The retrieved
     301             :      *  attribute  (which may be 0) is then parsed using TplConvert<XMLCh>::_2double.
     302             :      *  If the attribute is empty or ==0, TplConvert<XMLCh>::_2double throws an
     303             :      *  EmptyData-exception which is passed.
     304             :      * If the value can not be parsed to a double, TplConvert<XMLCh>::_2double throws a
     305             :      *  NumberFormatException-exception which is passed.
     306             :      *
     307             :      * @param[in] id The id of the attribute to return the value of
     308             :      * @return The attribute's value as a float, if it could be read and parsed
     309             :      * @exception EmptyData If the attribute is not known or the attribute value is an empty string
     310             :      * @exception NumberFormatException If the attribute value can not be parsed to an double
     311             :      */
     312       15676 :     inline double getFloat(int id) const {
     313       31352 :         return StringUtils::toDouble(getString(id));
     314             :     }
     315             : 
     316             : 
     317             :     /**
     318             :      * @brief Returns the double-value of the named attribute
     319             :      *
     320             :      * Tries to retrieve the attribute from the the attribute list. The retrieved
     321             :      *  attribute  (which may be 0) is then parsed using TplConvert<XMLCh>::_2double.
     322             :      *  If the attribute is empty or ==0, TplConvert<XMLCh>::_2double throws an
     323             :      *  EmptyData-exception which is passed.
     324             :      * If the value can not be parsed to a double, TplConvert<XMLCh>::_2double throws a
     325             :      *  NumberFormatException-exception which is passed.
     326             :      *
     327             :      * @param[in] id The name of the attribute to return the value of
     328             :      * @return The attribute's value as a float, if it could be read and parsed
     329             :      * @exception EmptyData If the attribute is not known or the attribute value is an empty string
     330             :      * @exception NumberFormatException If the attribute value can not be parsed to an double
     331             :      */
     332             :     virtual double getFloat(const std::string& id) const = 0;
     333             : 
     334             : 
     335             :     /**
     336             :      * @brief Returns the string-value of the named (by its enum-value) attribute
     337             :      *
     338             :      * Tries to retrieve the attribute from the the attribute list.
     339             :      *  If the attribute is ==0, TplConvert<XMLCh>::_2strSec returns the default value.
     340             :      * @param[in] id The name of the attribute to return the value of
     341             :      * @param[in] def The default value to return if the attribute is not in attributes
     342             :      * @return The attribute's value as a string, if it could be read and parsed
     343             :      */
     344             :     virtual std::string getStringSecure(const std::string& id,
     345             :                                         const std::string& def) const = 0;
     346             :     //}
     347             : 
     348             : 
     349             :     /** @brief Converts the given attribute id into a man readable string
     350             :      *
     351             :      * @param[in] attr The id of the attribute to return the name of
     352             :      * @return The name of the described attribute
     353             :      */
     354             :     virtual std::string getName(int attr) const = 0;
     355             : 
     356             :     /** @brief Prints all attribute names and values into the given stream
     357             :      *
     358             :      * @param[in] os The stream to use
     359             :      */
     360             :     virtual void serialize(std::ostream& os) const = 0;
     361             : 
     362             :     /** @brief Retrieves all attribute names
     363             :      */
     364             :     virtual std::vector<std::string> getAttributeNames() const = 0;
     365             : 
     366             :     /// @brief return the objecttype to which these attributes belong
     367             :     const std::string& getObjectType() const {
     368       10928 :         return myObjectType;
     369             :     }
     370             : 
     371             :     friend std::ostream& operator<<(std::ostream& os, const SUMOSAXAttributes& src);
     372             : 
     373             :     /// @brief return a new deep-copy attributes object
     374             :     virtual SUMOSAXAttributes* clone() const = 0;
     375             : 
     376             :     /** @brief The encoding of parsed strings */
     377             :     static const std::string ENCODING;
     378             : 
     379             : 
     380             : protected:
     381             :     template <typename T> T fromString(const std::string& value) const;
     382             :     void emitUngivenError(const std::string& attrname, const char* objectid) const;
     383             :     void emitEmptyError(const std::string& attrname, const char* objectid) const;
     384             :     void emitFormatError(const std::string& attrname, const std::string& type, const char* objectid) const;
     385             : 
     386             : private:
     387             :     /// @brief Invalidated copy constructor.
     388             :     SUMOSAXAttributes(const SUMOSAXAttributes& src) = delete;
     389             : 
     390             :     /// @brief Invalidated assignment operator.
     391             :     SUMOSAXAttributes& operator=(const SUMOSAXAttributes& src) = delete;
     392             : 
     393             :     /// @brief the object type to use in error reporting
     394             :     std::string myObjectType;
     395             : 
     396             : };
     397             : 
     398             : 
     399             : inline std::ostream& operator<<(std::ostream& os, const SUMOSAXAttributes& src) {
     400         136 :     src.serialize(os);
     401             :     return os;
     402             : }
     403             : 
     404             : 
     405             : template<typename X> struct invalid_return {
     406             :     static const X value;
     407             : };
     408             : 
     409             : #define INVALID_RETURN(TYPE) \
     410             : template<> struct invalid_return<TYPE> { \
     411             :     static const TYPE value; \
     412             : }
     413             : INVALID_RETURN(std::string);
     414             : INVALID_RETURN(int);
     415             : INVALID_RETURN(long long int);
     416             : INVALID_RETURN(double);
     417             : INVALID_RETURN(bool);
     418             : INVALID_RETURN(RGBColor);
     419             : INVALID_RETURN(Position);
     420             : INVALID_RETURN(PositionVector);
     421             : INVALID_RETURN(Boundary);
     422             : INVALID_RETURN(SumoXMLEdgeFunc);
     423             : INVALID_RETURN(SumoXMLNodeType);
     424             : INVALID_RETURN(RightOfWay);
     425             : INVALID_RETURN(FringeType);
     426             : INVALID_RETURN(ParkingType);
     427             : INVALID_RETURN(std::vector<std::string>);
     428             : INVALID_RETURN(std::vector<int>);
     429             : INVALID_RETURN(std::vector<double>);
     430             : 
     431             : 
     432             : template <typename T>
     433    48975036 : T SUMOSAXAttributes::get(int attr, const char* objectid,
     434             :                          bool& ok, bool report) const {
     435             :     try {
     436    48975036 :         bool isPresent = true;
     437    48975036 :         const std::string& strAttr = getString(attr, &isPresent);
     438    48975036 :         if (isPresent) {
     439    48974591 :             return fromString<T>(strAttr);
     440             :         }
     441         445 :         if (report) {
     442       15389 :             emitUngivenError(getName(attr), objectid);
     443             :         }
     444       14959 :     } catch (const FormatException& e) {
     445         418 :         if (report) {
     446         960 :             emitFormatError(getName(attr), e.what(), objectid);
     447             :         }
     448       28246 :     } catch (EmptyData&) {
     449       14123 :         if (report) {
     450        1142 :             emitEmptyError(getName(attr), objectid);
     451             :         }
     452             :     }
     453       14986 :     ok = false;
     454       13893 :     return invalid_return<T>::value;
     455             : }
     456             : 
     457             : 
     458             : template <typename T>
     459    53284254 : T SUMOSAXAttributes::getOpt(int attr, const char* objectid,
     460             :                             bool& ok, T defaultValue, bool report) const {
     461             :     try {
     462    53284254 :         bool isPresent = true;
     463    53284254 :         const std::string& strAttr = getString(attr, &isPresent);
     464    53284254 :         if (isPresent) {
     465     8369526 :             return fromString<T>(strAttr);
     466             :         }
     467       26804 :         return defaultValue;
     468         647 :     } catch (const FormatException& e) {
     469          74 :         if (report) {
     470         222 :             emitFormatError(getName(attr), e.what(), objectid);
     471             :         }
     472         998 :     } catch (EmptyData&) {
     473         499 :         if (report) {
     474         184 :             emitEmptyError(getName(attr), objectid);
     475             :         }
     476             :     }
     477         573 :     ok = false;
     478         100 :     return invalid_return<T>::value;
     479             : }

Generated by: LCOV version 1.14