73 typed_value() =
default;
75 explicit typed_value(T* bound_variable)
76 : m_bound_variable(bound_variable)
79 typed_value* default_value(
const T& value)
81 m_default_value = value;
86 typed_value* required()
92 typed_value* multitoken()
94 m_is_multitoken =
true;
98 std::any parse(
const std::string& s)
const override
100 return std::any(parse_impl(s));
103 T parse_impl(
const std::string& s)
const
106 if constexpr (std::is_same_v<T, std::string>) {
110 std::istringstream iss(s);
113 throw std::logic_error(
"Failed to parse option value \"" + s +
"\"");
118 std::string default_string()
const override
122 return default_string_impl(m_default_value);
125 static std::string default_string_impl(
const T& value)
127 if constexpr (std::is_same_v<T, std::string>) {
130 else if constexpr (std::is_same_v<T, bool>) {
131 return value ?
"true" :
"false";
134 std::ostringstream oss;
140 bool has_default()
const override {
return m_has_default; }
141 bool is_required()
const override {
return m_is_required; }
142 bool is_bool_switch()
const override {
return false; }
143 bool is_multitoken()
const override {
return m_is_multitoken; }
145 std::any default_value_any()
const override
147 return std::any(m_default_value);
150 void assign_bound(
const std::any& value)
const override
152 if (m_bound_variable)
153 *m_bound_variable = std::any_cast<T>(value);
158 T* m_bound_variable =
nullptr;
160 bool m_has_default{
false };
161 bool m_is_required{
false };
162 bool m_is_multitoken{
false };
175 typed_value() =
default;
177 explicit typed_value(
bool* bound_variable)
178 : m_bound_variable(bound_variable)
179 , m_default_value(
false)
180 , m_has_default(
true)
181 , m_is_bool_switch(
true)
184 typed_value* default_value(
const bool& value)
186 m_default_value = value;
187 m_has_default =
true;
191 typed_value* required()
193 m_is_required =
true;
197 typed_value* multitoken()
202 std::any parse(
const std::string& s)
const override
204 return std::any(parse_impl(s));
207 bool parse_impl(
const std::string& s)
const
209 if (s ==
"true" || s ==
"1" || s ==
"yes" || s ==
"on")
211 if (s ==
"false" || s ==
"0" || s ==
"no" || s ==
"off")
213 throw std::logic_error(
"Failed to parse bool option value \"" + s +
"\"");
216 std::string default_string()
const override
220 return m_default_value ?
"true" :
"false";
223 bool has_default()
const override {
return m_has_default; }
224 bool is_required()
const override {
return m_is_required; }
225 bool is_bool_switch()
const override {
return m_is_bool_switch; }
226 bool is_multitoken()
const override {
return false; }
228 std::any default_value_any()
const override
230 return std::any(m_default_value);
233 void assign_bound(
const std::any& value)
const override
235 if (m_bound_variable)
236 *m_bound_variable = std::any_cast<bool>(value);
241 bool* m_bound_variable =
nullptr;
242 bool m_default_value =
false;
243 bool m_has_default =
true;
244 bool m_is_bool_switch =
true;
245 bool m_is_required{
false };
258 typed_value() =
default;
260 explicit typed_value(std::vector<std::string>* bound_variable)
261 : m_bound_variable(bound_variable)
264 typed_value* default_value(
const std::vector<std::string>& value)
266 m_default_value = value;
267 m_has_default =
true;
271 typed_value* required()
273 m_is_required =
true;
277 typed_value* multitoken()
279 m_is_multitoken =
true;
283 std::any parse(
const std::string& s)
const override
285 std::vector<std::string> v;
287 return std::any(std::move(v));
290 std::string default_string()
const override
292 if (!m_has_default || m_default_value.empty())
295 for (
size_t i = 0; i < m_default_value.size(); ++i) {
298 result += m_default_value[i];
303 bool has_default()
const override {
return m_has_default; }
304 bool is_required()
const override {
return m_is_required; }
305 bool is_bool_switch()
const override {
return false; }
306 bool is_multitoken()
const override {
return m_is_multitoken; }
308 std::any default_value_any()
const override
310 return std::any(m_default_value);
313 void assign_bound(
const std::any& value)
const override
315 if (m_bound_variable)
316 *m_bound_variable = std::any_cast<std::vector<std::string>>(value);
321 std::vector<std::string>* m_bound_variable =
nullptr;
322 std::vector<std::string> m_default_value;
323 bool m_has_default{
false };
324 bool m_is_required{
false };
325 bool m_is_multitoken{
true };
425class ARCCORE_COMMON_EXPORT options_description
429 explicit options_description(
const std::string& title =
"Options");
434 class ARCCORE_COMMON_EXPORT options_proxy
438 explicit options_proxy(options_description& desc)
442 options_proxy& operator()(
const char* name,
const char* description);
444 const char* description);
447 template <
typename T>
448 options_proxy& operator()(
const char* name,
const typed_value<T>* value,
449 const char* description)
451 m_desc.add_option(name, std::shared_ptr<option_value>(
const_cast<typed_value<T>*
>(value)),
456 template <
typename T>
457 options_proxy& operator()(
const char* name,
const typed_value<T>* value)
459 m_desc.add_option(name, std::shared_ptr<option_value>(
const_cast<typed_value<T>*
>(value)),
466 options_description& m_desc;
471 void add_option(
const std::string& name,
472 std::shared_ptr<option_value> value_semantic,
473 const std::string& description);
475 const std::vector<option_descriptor>& options()
const {
return m_options; }
479 ARCCORE_COMMON_EXPORT
friend std::ostream& operator<<(std::ostream& os,
const options_description& desc);
483 std::vector<option_descriptor> m_options;
500 variable_value() =
default;
502 explicit variable_value(std::any value,
bool is_default =
false)
503 : m_value(std::move(value))
504 , m_is_default(is_default)
507 bool empty()
const {
return !m_value.has_value(); }
508 bool is_default()
const {
return m_is_default; }
510 template <
typename T>
514 return std::any_cast<T>(m_value);
516 catch (
const std::bad_any_cast&) {
517 throw std::logic_error(
"Type mismatch in variable_value::as<T>()");
521 void set_semantic(std::shared_ptr<option_value> semantic)
523 m_semantic = std::move(semantic);
526 const std::shared_ptr<option_value>& semantic()
const {
return m_semantic; }
527 std::any& value_ref() {
return m_value; }
532 bool m_is_default{
false };
533 std::shared_ptr<option_value> m_semantic;
537 bool count(
const std::string& name)
const;
540 void set_semantic(
const std::string& name, std::shared_ptr<option_value> semantic);
542 using iterator = std::map<std::string, variable_value>::iterator;
543 using const_iterator = std::map<std::string, variable_value>::const_iterator;
544 iterator begin() {
return m_values.begin(); }
545 iterator end() {
return m_values.end(); }
546 const_iterator begin()
const {
return m_values.begin(); }
547 const_iterator end()
const {
return m_values.end(); }
551 std::map<std::string, variable_value> m_values;
577class ARCCORE_COMMON_EXPORT parsed_options
584 std::vector<std::string> values;
593 void add_option(
const std::string& name, std::vector<std::string> values)
595 m_parsed.push_back({ name, std::move(values) });
598 const std::vector<parsed_option>& options()
const {
return m_parsed; }
602 const options_description* m_desc =
nullptr;
603 std::vector<parsed_option> m_parsed;