alpaqa pantr
Nonconvex constrained optimization
Loading...
Searching...
No Matches
params.tpp
Go to the documentation of this file.
2
5
6#include <charconv>
7#include <chrono>
8#include <concepts>
9#include <map>
10#include <numeric>
11#include <stdexcept>
12#include <string_view>
13#include <system_error>
14#include <tuple>
15#include <type_traits>
16
17namespace alpaqa::params {
18
20
21/// Throw a meaningful error when `s.key` is not empty, to indicate that
22/// the given type @p T is not of struct type and cannot be indexed into.
23template <class T>
25 if (!s.key.empty())
26 throw invalid_param("Type '" + demangled_typename(typeid(T)) +
27 "' cannot be indexed in '" +
28 std::string(s.full_key) + "'");
29}
30
31/// Throw a meaningful error to indicate that parameters of type @p T are not
32/// supported or implemented.
33template <class T>
34void unsupported_type(T &, [[maybe_unused]] ParamString s) {
35 throw invalid_param("Unknown parameter type '" +
36 demangled_typename(typeid(T)) + "' in '" +
37 std::string(s.full_key) + "'");
38}
39
40template <>
41void set_param(bool &b, ParamString s);
42
43template <>
44void set_param(std::string_view &v, ParamString s);
45
46template <>
47void set_param(std::string &v, ParamString s);
48
49template <class T>
50 requires((std::floating_point<T> || std::integral<T>) && !std::is_enum_v<T>)
51void set_param(T &f, ParamString s);
52
53template <>
54void set_param(vec<config_t> &v, ParamString s);
55
56template <class Rep, class Period>
57void set_param(std::chrono::duration<Rep, Period> &t, ParamString s);
58
59/// Return a function that applies @ref set_param to the given attribute of a
60/// value of type @p T.
61template <class T, class A>
62auto param_setter(A T::*attr) {
63 return [attr](T &t, ParamString s) { return set_param(t.*attr, s); };
64}
65
66/// Function wrapper to set attributes of a struct, type-erasing the type of the
67/// attribute.
68template <class T>
70 template <class A>
71 param_setter_fun_t(A T::*attr) : set(param_setter(attr)) {}
72 std::function<void(T &, ParamString)> set;
73 void operator()(T &t, ParamString s) const { return set(t, s); }
74};
75
76/// Dictionary that maps struct attribute names to type-erased functions that
77/// set those attributes.
78template <class T>
80 std::map<std::string_view, param_setter_fun_t<T>>;
81
82/// Specialize this type to define the attribute name to attribute setters
83/// dictionaries for a struct type @p T.
84template <class T>
86
87/// Return a string enumerating the possible attribute names for the struct type
88/// @p T.
89template <class T>
91 const auto &tbl = dict_to_struct_table<T>::table;
92 if (tbl.empty())
93 return std::string{};
94 auto penult = std::prev(tbl.end());
95 auto quote_concat = [](std::string &&a, auto b) {
96 return a + "'" + std::string(b.first) + "', ";
97 };
98 return std::accumulate(tbl.begin(), penult, std::string{}, quote_concat) +
99 "'" + std::string(penult->first) + "'";
100}
101
102/// Use @p s to index into the struct type @p T and overwrite the attribute
103/// given by @p s.key.
104template <class T>
105 requires requires { dict_to_struct_table<T>::table; }
106void set_param(T &t, ParamString s) {
107 const auto &m = dict_to_struct_table<T>::table;
108 auto [key, remainder] = split_key(s.key);
109 auto it = m.find(key);
110 if (it == m.end())
111 throw invalid_param("Invalid key '" + std::string(key) +
112 "' for type '" + demangled_typename(typeid(T)) +
113 "' in '" + std::string(s.full_key) +
114 "',\n possible keys are: " + possible_keys<T>());
115 s.key = remainder;
116 it->second.set(t, s);
117}
118
119/// Helper macro to easily specialize @ref alpaqa::params::dict_to_struct_table.
120#define PARAMS_TABLE(type_, ...) \
121 template <> \
122 struct dict_to_struct_table<type_> { \
123 using type = type_; \
124 inline static const dict_to_struct_table_t<type> table{__VA_ARGS__}; \
125 }
126
127/// Helper macro to easily initialize a
128/// @ref alpaqa::params::dict_to_struct_table_t.
129#define PARAMS_MEMBER(name) \
130 { \
131#name, &type::name \
132 }
133
134} // namespace alpaqa::params
std::string demangled_typename(const std::type_info &t)
Get the pretty name of the given type as a string.
void set_param(bool &b, ParamString s)
Definition: params.cpp:21
auto param_setter(A T::*attr)
Return a function that applies set_param to the given attribute of a value of type T.
Definition: params.tpp:62
void unsupported_type(T &, ParamString s)
Throw a meaningful error to indicate that parameters of type T are not supported or implemented.
Definition: params.tpp:34
std::string_view key
The subkey to resolve next.
Definition: params.hpp:19
void assert_key_empty(ParamString s)
Throw a meaningful error when s.key is not empty, to indicate that the given type T is not of struct ...
Definition: params.tpp:24
std::string_view full_key
Full key string, used for diagnostics.
Definition: params.hpp:17
auto split_key(std::string_view full, char tok='.')
Split the string full on the first occurrence of tok.
Definition: params.hpp:31
std::map< std::string_view, param_setter_fun_t< T > > dict_to_struct_table_t
Dictionary that maps struct attribute names to type-erased functions that set those attributes.
Definition: params.tpp:80
auto possible_keys()
Return a string enumerating the possible attribute names for the struct type T.
Definition: params.tpp:90
Represents a parameter value encoded as a string in the format abc.def.key=value.
Definition: params.hpp:15
Specialize this type to define the attribute name to attribute setters dictionaries for a struct type...
Definition: params.tpp:85
typename Conf::vec vec
Definition: config.hpp:52
Custom parameter parsing exception.
Definition: params.hpp:25
Function wrapper to set attributes of a struct, type-erasing the type of the attribute.
Definition: params.tpp:69
std::function< void(T &, ParamString)> set
Definition: params.tpp:72
void operator()(T &t, ParamString s) const
Definition: params.tpp:73