cepgen is hosted by Hepforge, IPPP Durham
CepGen 1.2.5
Central exclusive processes event generator
Loading...
Searching...
No Matches
BoostTreeUtils.cpp
Go to the documentation of this file.
1/*
2 * CepGen: a central exclusive processes event generator
3 * Copyright (C) 2020-2024 Laurent Forthomme
4 *
5 * This program is free software: you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation, either version 3 of the License, or
8 * any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program. If not, see <http://www.gnu.org/licenses/>.
17 */
18
19#include <pthread.h>
20
25
26namespace boost {
27 namespace cepgen {
28 pt::ptree pack(const ::cepgen::RunParameters&) {
29 pt::ptree out;
30 return out;
31 }
32
33 pt::ptree pack(const ::cepgen::ParametersDescription& pdesc) { return pack(pdesc.parameters()); }
34
35 pt::ptree pack(const ::cepgen::ParametersList& params) {
36 pt::ptree out;
37 for (const auto& key : params.keys()) {
38 if (params.has<::cepgen::ParametersList>(key))
39 out.add_child(key, pack(params.get<::cepgen::ParametersList>(key)));
40 else if (params.has<bool>(key))
41 out.put(key, params.get<bool>(key));
42 else if (params.has<int>(key))
43 out.put(key, params.get<int>(key));
44 else if (params.has<unsigned long long>(key))
45 out.put(key, params.get<unsigned long long>(key));
46 else if (params.has<double>(key)) {
47 std::ostringstream os; // ensure floating point storage
48 os << std::scientific << params.get<double>(key);
49 out.put(key, os.str());
50 } else if (params.has<std::string>(key))
51 out.put(key, params.get<std::string>(key));
52 else if (params.has<::cepgen::Limits>(key))
53 out.add_child(key, pack(params.get<::cepgen::Limits>(key)));
54 else if (params.has<std::vector<::cepgen::ParametersList>>(key))
55 out.add_child(key, pack(params.get<std::vector<::cepgen::ParametersList>>(key)));
56 else if (params.has<std::vector<int>>(key))
57 out.add_child(key, pack(params.get<std::vector<int>>(key)));
58 else if (params.has<std::vector<double>>(key))
59 out.add_child(key, pack(params.get<std::vector<double>>(key)));
60 else if (params.has<std::vector<std::string>>(key))
61 out.add_child(key, pack(params.get<std::vector<std::string>>(key)));
62 else
63 throw ::cepgen::Exception(
64 __FUNC__, "boost::cepgen::pack", ::cepgen::Exception::Type::fatal, __FILE__, __LINE__)
65 << "Failed to recast the key \"" << key << "\" "
66 << "with value \"" << params.getString(key) << "\"!";
67 }
68 return out;
69 }
70
71 template <>
72 pt::ptree pack<::cepgen::ParametersList>(const std::vector<::cepgen::ParametersList>& vec) {
73 pt::ptree out;
74 std::transform(vec.begin(), vec.end(), std::back_inserter(out), [](const auto& elem) {
75 return std::make_pair("", pack(elem));
76 });
77 return out;
78 }
79
80 template <typename T>
81 pt::ptree pack(const std::vector<T>& vec) {
82 pt::ptree out;
83 for (const auto& elem : vec) {
84 pt::ptree elem_tree;
85 elem_tree.put("", elem);
86 out.push_back(std::make_pair("", elem_tree));
87 }
88 return out;
89 }
90
91 template <>
92 pt::ptree pack<double>(const std::vector<double>& vec) {
93 pt::ptree out;
94 for (const auto& elem : vec) {
95 pt::ptree elem_tree;
96 std::ostringstream os; // ensure floating point storage
97 os << std::scientific << elem;
98 elem_tree.put("", elem);
99 out.push_back(std::make_pair("", elem_tree));
100 }
101 return out;
102 }
103
104 pt::ptree pack(const ::cepgen::Limits& lim) {
105 pt::ptree out;
106 if (lim.hasMin()) {
107 pt::ptree min;
108 std::ostringstream os; // ensure floating point storage
109 os << std::scientific << lim.min();
110 min.put("", os.str());
111 out.push_back(std::make_pair(MIN_KEY, min));
112 }
113 if (lim.hasMax()) {
114 pt::ptree max;
115 std::ostringstream os; // ensure floating point storage
116 os << std::scientific << lim.max();
117 max.put("", os.str());
118 out.push_back(std::make_pair(MAX_KEY, max));
119 }
120 return out;
121 }
122
123 ::cepgen::ParametersList unpack(const pt::ptree& tree) {
125 if (tree.empty())
126 return out;
127 for (const auto& it : tree) {
128 try { // this might be a vector
129 if (it.first.empty())
130 try { // try to parse as a parameters list
131 out.operator[]<std::vector<::cepgen::ParametersList>>(DAUGH_KEY).emplace_back(unpack(it.second));
132 } catch (const boost::exception&) {
133 try { // try to parse as a float
134 out.operator[]<std::vector<double>>(DAUGH_KEY).emplace_back(it.second.get_value<double>());
135 } catch (const boost::exception&) {
136 try { // try to parse as an integer
137 out.operator[]<std::vector<int>>(DAUGH_KEY).emplace_back(it.second.get_value<int>());
138 } catch (const boost::exception&) { // does not work, must be a string
139 out.operator[]<std::vector<std::string>>(DAUGH_KEY).emplace_back(it.second.get_value<std::string>());
140 }
141 }
142 }
143 else
144 add(out, it.first, it.second);
145 } catch (const ::cepgen::Exception&) {
146 if (it.second.get_value<std::string>().find('.') != std::string::npos)
147 try { // try to parse float if contains a '.'
148 out.set<double>(it.first, it.second.get_value<double>());
149 } catch (const boost::exception&) { // does not work as a float, must be a string
150 out.set<std::string>(it.first, it.second.get_value<std::string>());
151 }
152 else
153 try { // try to parse integer
154 out.set<int>(it.first, it.second.get_value<int>());
155 } catch (const boost::exception&) { // does not work as an integer, must be a string
156 out.set<std::string>(it.first, it.second.get_value<std::string>());
157 }
158 }
159 }
160 return out;
161 }
162
163 void add(::cepgen::ParametersList& base, const std::string& name, const pt::ptree& tree) {
164 auto plist = unpack(tree);
165 //--- first check if we have a limits set
166 if (plist.keys().size() <= 2 && (plist.has<double>(MIN_KEY) || plist.has<double>(MAX_KEY))) {
167 // we might have a (min, max) limit
169 plist.fill<double>(MIN_KEY, lim.min());
170 plist.fill<double>(MAX_KEY, lim.max());
171 base.set<::cepgen::Limits>(name, lim);
172 }
173 //--- then check if daughter is a vector; if true, skip one hierarchy level
174 else if (plist.has<std::vector<int>>(DAUGH_KEY))
175 base.set<std::vector<int>>(name, plist.get<std::vector<int>>(DAUGH_KEY));
176 else if (plist.has<std::vector<double>>(DAUGH_KEY)) {
177 auto vec = plist.get<std::vector<double>>(DAUGH_KEY);
178 base.set<std::vector<double>>(name, vec);
179 } else if (plist.has<std::vector<std::string>>(DAUGH_KEY))
180 base.set<std::vector<std::string>>(name, plist.get<std::vector<std::string>>(DAUGH_KEY));
181 else
182 base.set<::cepgen::ParametersList>(name, plist);
183 }
184
185 } // namespace cepgen
186} // namespace boost
#define __FUNC__
Definition Message.h:209
@ fatal
Critical and stopping error.
Definition Exception.h:31
Validity interval for a variable.
Definition Limits.h:28
double min() const
Lower limit to apply on the variable.
Definition Limits.h:52
double max() const
Upper limit to apply on the variable.
Definition Limits.h:54
T get(const std::string &key, const T &def=default_arg< T >::get()) const
Get a parameter value.
ParametersList & set(const std::string &, const T &)
Set a parameter value Set a recast parameter value.
::cepgen::ParametersList unpack(const pt::ptree &tree)
static constexpr const char * MIN_KEY
static constexpr const char * MAX_KEY
pt::ptree pack<::cepgen::ParametersList >(const std::vector<::cepgen::ParametersList > &vec)
pt::ptree pack< double >(const std::vector< double > &vec)
static constexpr const char * DAUGH_KEY
pt::ptree pack(const ::cepgen::RunParameters &)
void add(::cepgen::ParametersList &base, const std::string &name, const pt::ptree &tree)
Common namespace for this Monte Carlo generator.