configset.hh

Go to the documentation of this file.
00001 #ifndef UTILMM_CONFIG_SET_HH
00002 #define UTILMM_CONFIG_SET_HH
00003 
00004 #include <map>
00005 #include <string>
00006 #include <boost/noncopyable.hpp>
00007 #include <boost/lexical_cast.hpp>
00008 #include <boost/utility/enable_if.hpp>
00009 
00010 #include <list>
00011 
00012 namespace utilmm
00013 {
00014     /* To discriminate between list and non-list get<> */
00015     namespace details
00016     {
00017         template<typename T> struct is_list
00018         { static const bool value = false; };
00019         template<typename T> struct is_list< std::list<T> >
00020         { static const bool value = true; };
00021     }
00022 
00024     class config_set 
00025         : private boost::noncopyable
00026     {
00027         friend class ConfigFile;
00028 
00029     private:
00030         typedef std::list<std::string> stringlist;
00031         template<typename T>
00032         static T convert(std::string const& value);
00033         
00034     protected:
00035         config_set* m_parent;
00036         typedef std::multimap<std::string, std::string> ValueMap;
00037         ValueMap m_values;
00038         typedef std::multimap<std::string, const config_set*> ChildMap;
00039         ChildMap m_children;
00040 
00041     protected:
00043         void clear();
00044         
00045     public:
00046         explicit config_set(config_set* parent = 0);
00047         ~config_set();
00048         
00049         typedef std::list<const config_set*> subsets;
00050 
00052         bool empty() const;
00053 
00055         bool exists (const std::string& attribute) const;
00056         
00060         const config_set* parent() const;
00061         config_set* parent();
00062 
00064         std::list<const config_set*> children(const std::string& name) const;
00066         config_set const& child(std::string const& name) const;
00067 
00069         template<typename T> 
00070         T get(std::string const& name, T const& defval = T(),
00071                 typename boost::enable_if< details::is_list<T> >::type *enabler = 0) const;
00074         template<typename T> 
00075         T get(std::string const& name, T const& defval = T(),
00076                 typename boost::disable_if< details::is_list<T> >::type *enabler = 0) const;
00077 
00079         void set(std::string const& name, std::string const& value);
00081         void set(std::string const& name, std::list<std::string> const& value);
00083         void insert(std::string const& name, std::string const& value);
00085         void insert(std::string const& name, std::list<std::string> const& value);
00087         void insert(std::string const& name, config_set const* value);
00089         void erase(std::string const& name);
00090     };
00091 
00092     namespace details {
00093         typedef std::list<std::string> stringlist;
00094     }
00095 
00096     template<> bool config_set::convert(std::string const& value);
00097     template<typename T> 
00098     T config_set::convert(const std::string& value)
00099     { return boost::lexical_cast<T>(value); }
00100 
00101 
00105     template<>
00106     config_set::stringlist config_set::get(std::string const& name,
00107             config_set::stringlist const& defval,
00108             boost::enable_if< details::is_list<config_set::stringlist> >::type *enabler) const;
00109 
00111     template<typename T> 
00112     T config_set::get(std::string const& name, T const& defval,
00113             typename boost::enable_if< details::is_list<T> >::type *enabler) const
00114     {
00115         stringlist values = get< stringlist >(name);
00116         if (values.empty())
00117             return defval;
00118         
00119         T result;
00120         for (stringlist::const_iterator it = values.begin(); it != values.end(); ++it)
00121             result.push_back(convert<typename T::value_type>(*it));
00122 
00123         return result;
00124     }
00125 
00127     template<typename T>
00128     T config_set::get(std::string const& name, T const& defval,
00129             typename boost::disable_if< details::is_list<T> >::type *enabler) const
00130     {   
00131         std::list<T> deflist;
00132         deflist.push_back(defval);
00133         return get< std::list<T> >(name, deflist).front();
00134     }
00135 }
00136 
00137 #endif
00138 
00139 
00140 

Generated on Tue Feb 19 10:51:01 2008 for Util-- by doxygen 1.5.3
SourceForge.net Project Page