1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220
|
// Copyright Vladimir Prus 2002-2004.
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt
// or copy at http://www.boost.org/LICENSE_1_0.txt)
#ifndef BOOST_VARIABLES_MAP_VP_2003_05_19
#define BOOST_VARIABLES_MAP_VP_2003_05_19
#include <boost/program_options/config.hpp>
#include <boost/any.hpp>
#include <boost/shared_ptr.hpp>
#include <string>
#include <map>
#include <set>
#if defined(BOOST_MSVC)
# pragma warning (push)
# pragma warning (disable:4251) // 'boost::program_options::variable_value::v' : class 'boost::any' needs to have dll-interface to be used by clients of class 'boost::program_options::variable_value
#endif
namespace boost { namespace program_options {
template<class charT>
class basic_parsed_options;
class value_semantic;
class variables_map;
// forward declaration
/** Stores in 'm' all options that are defined in 'options'.
If 'm' already has a non-defaulted value of an option, that value
is not changed, even if 'options' specify some value.
*/
BOOST_PROGRAM_OPTIONS_DECL
void store(const basic_parsed_options<char>& options, variables_map& m,
bool utf8 = false);
/** Stores in 'm' all options that are defined in 'options'.
If 'm' already has a non-defaulted value of an option, that value
is not changed, even if 'options' specify some value.
This is wide character variant.
*/
BOOST_PROGRAM_OPTIONS_DECL
void store(const basic_parsed_options<wchar_t>& options,
variables_map& m);
/** Runs all 'notify' function for options in 'm'. */
BOOST_PROGRAM_OPTIONS_DECL void notify(variables_map& m);
/** Class holding value of option. Contains details about how the
value is set and allows to conveniently obtain the value.
*/
class BOOST_PROGRAM_OPTIONS_DECL variable_value {
public:
variable_value() : m_defaulted(false) {}
variable_value(const boost::any& xv, bool xdefaulted)
: v(xv), m_defaulted(xdefaulted)
{}
/** If stored value if of type T, returns that value. Otherwise,
throws boost::bad_any_cast exception. */
template<class T>
const T& as() const {
return boost::any_cast<const T&>(v);
}
/** @overload */
template<class T>
T& as() {
return boost::any_cast<T&>(v);
}
/// Returns true if no value is stored.
bool empty() const;
/** Returns true if the value was not explicitly
given, but has default value. */
bool defaulted() const;
/** Returns the contained value. */
const boost::any& value() const;
/** Returns the contained value. */
boost::any& value();
private:
boost::any v;
bool m_defaulted;
// Internal reference to value semantic. We need to run
// notifications when *final* values of options are known, and
// they are known only after all sources are stored. By that
// time options_description for the first source might not
// be easily accessible, so we need to store semantic here.
shared_ptr<const value_semantic> m_value_semantic;
friend BOOST_PROGRAM_OPTIONS_DECL
void store(const basic_parsed_options<char>& options,
variables_map& m, bool);
friend class BOOST_PROGRAM_OPTIONS_DECL variables_map;
};
/** Implements string->string mapping with convenient value casting
facilities. */
class BOOST_PROGRAM_OPTIONS_DECL abstract_variables_map {
public:
abstract_variables_map();
abstract_variables_map(const abstract_variables_map* next);
virtual ~abstract_variables_map() {}
/** Obtains the value of variable 'name', from *this and
possibly from the chain of variable maps.
- if there's no value in *this.
- if there's next variable map, returns value from it
- otherwise, returns empty value
- if there's defaulted value
- if there's next variable map, which has a non-defaulted
value, return that
- otherwise, return value from *this
- if there's a non-defaulted value, returns it.
*/
const variable_value& operator[](const std::string& name) const;
/** Sets next variable map, which will be used to find
variables not found in *this. */
void next(abstract_variables_map* next);
private:
/** Returns value of variable 'name' stored in *this, or
empty value otherwise. */
virtual const variable_value& get(const std::string& name) const = 0;
const abstract_variables_map* m_next;
};
/** Concrete variables map which store variables in real map.
This class is derived from std::map<std::string, variable_value>,
so you can use all map operators to examine its content.
*/
class BOOST_PROGRAM_OPTIONS_DECL variables_map : public abstract_variables_map,
public std::map<std::string, variable_value>
{
public:
variables_map();
variables_map(const abstract_variables_map* next);
// Resolve conflict between inherited operators.
const variable_value& operator[](const std::string& name) const
{ return abstract_variables_map::operator[](name); }
// Override to clear some extra fields.
void clear();
void notify();
private:
/** Implementation of abstract_variables_map::get
which does 'find' in *this. */
const variable_value& get(const std::string& name) const;
/** Names of option with 'final' values \-- which should not
be changed by subsequence assignments. */
std::set<std::string> m_final;
friend BOOST_PROGRAM_OPTIONS_DECL
void store(const basic_parsed_options<char>& options,
variables_map& xm,
bool utf8);
/** Names of required options, filled by parser which has
access to options_description.
The map values are the "canonical" names for each corresponding option.
This is useful in creating diagnostic messages when the option is absent. */
std::map<std::string, std::string> m_required;
};
/*
* Templates/inlines
*/
inline bool
variable_value::empty() const
{
return v.empty();
}
inline bool
variable_value::defaulted() const
{
return m_defaulted;
}
inline
const boost::any&
variable_value::value() const
{
return v;
}
inline
boost::any&
variable_value::value()
{
return v;
}
}}
#if defined(BOOST_MSVC)
# pragma warning (pop)
#endif
#endif
|