8#include <trg/cdc/NeuroTriggerParameters.h>
12#include "boost/iostreams/filter/gzip.hpp"
13#include "boost/iostreams/filtering_streambuf.hpp"
14#include "boost/iostreams/filtering_stream.hpp"
15#include "boost/multi_array.hpp"
18#include <framework/core/Module.h>
23NeuroTriggerParameters::NeuroTriggerParameters(std::string& filename)
33 std::ifstream confile;
35 confile.open(filename, std::ifstream::in);
38 B2ERROR(
"Configuration file " + filename +
" could not be loaded! Make sure to give the configuration file as a parameter. \
39 An example file neuroconfig_example.conf has been saved.");
44 if (!confile.is_open()) {
46 B2ERROR(
"Configuration file " + filename +
" could not be loaded! Make sure to give the configuration file as a parameter. \
47 An example file neuroconfig_example.conf has been saved.");
50 while (std::getline(confile, line_all)) {
52 std::size_t hashtag = line_all.find(
'#');
53 std::string line = line_all.substr(0, hashtag);
57 if (line.length() < 3) {
62 if (line.find(
'=') == std::string::npos) {
65 line.erase(std::remove(line.begin(), line.end(),
' '), line.end());
66 par = line.substr(0, line.find(
'='));
68 l = line.substr(line.find(
"=") + 1, 1);
73 key = (locked) ? line.substr((line.find(
'=') + 2), line.length() - line.find(
'=') - 2) : line.substr((line.find(
'=') + 1),
74 line.length() - line.find(
'=') - 1);
75 if (par ==
"nInput") {
77 if (locked) {
nInput.lock();}
78 }
else if (par ==
"nOutput") {
81 }
else if (par ==
"relevantCut") {
84 }
else if (par ==
"nMLP") {
85 nMLP = std::stoul(key);
86 if (locked) {
nMLP.lock();}
87 }
else if (par ==
"targetZ") {
90 }
else if (par ==
"targetTheta") {
93 }
else if (par ==
"multiplyHidden") {
96 }
else if (par ==
"rescaleTarget") {
99 }
else if (par ==
"cutSum") {
101 if (locked) {
cutSum.lock();}
102 }
else if (par ==
"tMax") {
103 tMax = std::stoul(key);
104 if (locked) {
tMax.lock();}
105 }
else if (par ==
"ETOption") {
108 }
else if (par ==
"IDRanges") {
110 }
else if (par ==
"phiRangeUse") {
112 }
else if (par ==
"thetaRangeUse") {
114 }
else if (par ==
"invptRangeUse") {
116 }
else if (par ==
"phiRangeTrain") {
118 }
else if (par ==
"thetaRangeTrain") {
120 }
else if (par ==
"invptRangeTrain") {
122 }
else if (par ==
"nHidden") {
124 }
else if (par ==
"maxHitsPerSL") {
126 }
else if (par ==
"outputScale") {
128 }
else if (par ==
"SLpattern") {
130 }
else if (par ==
"SLpatternMask") {
132 }
else if (par ==
"precision") {
134 }
else if (par ==
"AdditionWireMode") {
136 }
else if (par ==
"AdditionInputPerSL") {
145 if (vec.size() < 1) {
return false;}
146 else if (vec[0].size() < 1) {
return false;}
147 else {
return vec[0][0].isSet();}
154 if (vec.size() < 1) {
return false;}
155 else {
return vec[0].isSet();}
162 std::ofstream savestream;
163 savestream.open(filename);
164 savestream <<
"########################################################" << std::endl;
165 savestream <<
"### Neurotrigger configuration file created by basf2 ###" << std::endl;
166 savestream <<
"########################################################" << std::endl << std::endl;
167 savestream <<
"# '=' means the parameter is set and can be changed," << std::endl;
168 savestream <<
"# '==' means the parameter is locked and should not be changed." << std::endl << std::endl;
170 savestream <<
"# number of input nodes " << std::endl;
172 savestream <<
"nInput " << (
nInput.isLocked() ?
"== " :
"= ") <<
nInput << std::endl;
173 savestream << std::endl;
174 }
else {savestream <<
"nInput = 27" << std::endl;}
175 savestream <<
"# number of output nodes " << std::endl;
177 savestream <<
"nOutput " << (
nOutput.isLocked() ?
"== " :
"= ") <<
nOutput << std::endl;
178 savestream << std::endl;
179 }
else {savestream <<
"nOutput = 2" << std::endl;}
180 savestream <<
"# If true, relevantCut is applied to the sum over hit counters, " << std::endl;
181 savestream <<
"# otherwise directly on the hit counters." << std::endl;
183 savestream <<
"cutSum " << (
cutSum.isLocked() ?
"== " :
"= ") <<
cutSum << std::endl;
184 savestream << std::endl;
185 }
else {savestream <<
"cutSum = 0" << std::endl;}
186 savestream <<
"# only used in the idhist module. it defines the how much of the idrange is cut off after making the histogram " <<
190 savestream << std::endl;
191 }
else {savestream <<
"relevantCut = 0.02" << std::endl;}
192 savestream <<
"# flag to allow for target tracks lying out of the output range to be rescaled during training. " << std::endl;
195 savestream << std::endl;
196 }
else {savestream <<
"rescaleTarget = 0" << std::endl;}
197 savestream <<
"# Number of networks. For network specific parameters you can give " << std::endl;
198 savestream <<
"# either a list with values for each network, or a single value that will be used" << std::endl;
199 savestream <<
"# for all. The ranges are also valid if nPhi * nPt * nTheta * nPattern = nMLPs. " << std::endl;
201 savestream <<
"nMLP " << (
nMLP.isLocked() ?
"== " :
"= ") <<
nMLP << std::endl;
202 savestream << std::endl;
203 }
else {savestream <<
"nMLP = 5" << std::endl;}
204 savestream <<
"# train z as output " << std::endl;
206 savestream <<
"targetZ " << (
targetZ.isLocked() ?
"== " :
"= ") <<
targetZ << std::endl;
207 savestream << std::endl;
208 }
else {savestream <<
"targetZ = 1" << std::endl;}
209 savestream <<
"# train theta as output " << std::endl;
212 savestream << std::endl;
213 }
else {savestream <<
"targetTheta = 1" << std::endl;}
214 savestream <<
"# If true, multiply nHidden with number of input nodes. " << std::endl;
217 savestream << std::endl;
218 }
else {savestream <<
"multiplyHidden = 0" << std::endl;}
219 savestream <<
"# Maximal drift time, identical for all networks. " << std::endl;
221 savestream <<
"tMax " << (
tMax.isLocked() ?
"== " :
"= ") <<
tMax << std::endl;
222 savestream << std::endl;
223 }
else {savestream <<
"tMax = 256" << std::endl;}
224 savestream <<
"# Determine, how the event time should be obtained. The options are:" << std::endl;
225 for (
unsigned i = 0; i < 11; i++) {
226 savestream <<
"# " << i <<
": " << to_strTiming(i) << std::endl;
229 savestream <<
"ETOption " << (
ETOption.isLocked() ?
"== " :
"= ") <<
ETOption << std::endl;
230 savestream << std::endl;
231 }
else {savestream <<
"ETOption = 7" << std::endl;}
232 savestream <<
"# Phi region for which MLP is used in degree for all networks. " << std::endl;
234 savestream << print2dArray<float>(
"phiRangeUse",
phiRangeUse);
235 savestream << std::endl;
236 }
else {savestream <<
"phiRangeUse = [[0, 360]]" << std::endl;}
237 savestream <<
"# relative ID range of the relevant wire IDs of the track segments " << std::endl;
238 savestream <<
"# that are taken into consideration when determining the best fitting track segments. " << std::endl;
240 savestream << print2dArray<float>(
"IDRanges",
IDRanges);
241 savestream << std::endl;
243 savestream <<
"IDRanges = [[0,-1.5,1.5,-7.5,-0.5,-1.5,1.5,0.5,7.5,-1.5,1.5,-8.5,0.5,-2.5,1.5,-0.5,10.5,-3.5,2.5],";
244 savestream <<
"[1,-1.5,1.5,-7.5,-0.5,-1.5,1.5,0.5,7.5,-1.5,1.5,-8.5,0.5,-2.5,1.5,-0.5,10.5,-3.5,2.5],";
245 savestream <<
"[2,-1.5,1.5,-7.5,-0.5,-1.5,1.5,0.5,7.5,-1.5,1.5,-8.5,0.5,-2.5,1.5,-0.5,10.5,-3.5,2.5],";
246 savestream <<
"[3,-1.5,1.5,-7.5,-0.5,-1.5,1.5,0.5,7.5,-1.5,1.5,-8.5,0.5,-2.5,1.5,-0.5,10.5,-3.5,2.5],";
247 savestream <<
"[4,-1.5,1.5,-7.5,-0.5,-1.5,1.5,0.5,7.5,-1.5,1.5,-8.5,0.5,-2.5,1.5,-0.5,10.5,-3.5,2.5]]";
248 savestream << std::endl;
250 savestream <<
"# Theta region for which MLP is used in degree for all networks. " << std::endl;
252 savestream << print2dArray<float>(
"thetaRangeUse",
thetaRangeUse);
253 savestream << std::endl;
254 }
else {savestream <<
"thetaRangeUse = [[10, 170]]" << std::endl;}
255 savestream <<
"# Charge / Pt region for which MLP is used in 1/GeV for all networks. " << std::endl;
257 savestream << print2dArray<float>(
"invptRangeUse",
invptRangeUse);
258 savestream << std::endl;
259 }
else {savestream <<
"invptRangeUse = [[-5, 5]]" << std::endl;}
260 savestream <<
"# Phi region for which MLP is trained in degree for all networks. " << std::endl;
261 savestream <<
"# Can be larger than use range to avoid edge effects. " << std::endl;
263 savestream << print2dArray<float>(
"phiRangeTrain",
phiRangeTrain);
264 savestream << std::endl;
265 }
else {savestream <<
"phiRangeTrain = [[0, 360]]" << std::endl;}
266 savestream <<
"# Theta region for which MLP is trained in degree for all networks. " << std::endl;
267 savestream <<
"# Can be larger than use range to avoid edge effects. " << std::endl;
270 savestream << std::endl;
271 }
else {savestream <<
"thetaRangeTrain = [[10, 170]]" << std::endl;}
272 savestream <<
"# charge/Pt region for which MLP is trained in degree for all networks. " << std::endl;
273 savestream <<
"# Can be larger than use range to avoid edge effects. " << std::endl;
276 savestream << std::endl;
277 }
else {savestream <<
"invptRangeTrain = [[-5, 5]]" << std::endl;}
278 savestream <<
"# Number of nodes in each hidden layer for all networks" << std::endl;
279 savestream <<
"# or factor to multiply with number of inputs." << std::endl;
280 savestream <<
"# The number of layers is derived from the shape." << std::endl;
282 savestream << print2dArray<float>(
"nHidden",
nHidden);
283 savestream << std::endl;
284 }
else {savestream <<
"nHidden = [[81]]" << std::endl;}
285 savestream <<
"# Maximum number of hits in a single super layer for all networks. " << std::endl;
287 savestream << print1dArray<unsigned short>(
"maxHitsPerSL",
maxHitsPerSL);
288 savestream << std::endl;
289 }
else {savestream <<
"maxHitsPerSL = [1]" << std::endl;}
290 savestream <<
"# Output scale for all networks. " << std::endl;
292 savestream << print2dArray<float>(
"outputScale",
outputScale);
293 savestream << std::endl;
294 }
else {savestream <<
"outputScale = [[-100, 100, 10, 170]]" << std::endl;}
295 savestream <<
"# Super layer pattern for which MLP is trained for all networks." << std::endl;
296 savestream <<
"# Binary pattern of 9 * maxHitsPerSL bits (on/off for each hit)." << std::endl;
297 savestream <<
"# 0 in bit <i>: hits from super layer <i> are not used." << std::endl;
298 savestream <<
"# 1 in bit <i>: hits from super layer <i> are used." << std::endl;
299 savestream <<
"# SLpattern = 0: use any hits present, don't check the pattern. " << std::endl;
301 savestream << print1dArray<unsigned long>(
"SLpattern",
SLpattern);
302 savestream << std::endl;
303 }
else {savestream <<
"SLpattern = [511, 383, 479, 503, 509]" << std::endl;}
304 savestream <<
"# Super layer pattern mask for which MLP is trained for all networks." << std::endl;
305 savestream <<
"# Binary pattern of 9 * maxHitsPerSL bits (on/off for each hit)." << std::endl;
306 savestream <<
"# 0 in bit <i>: super layer <i> may or may not have a hit." << std::endl;
307 savestream <<
"# 1 in bit <i>: super layer <i>" << std::endl;
308 savestream <<
"# - must have a hit if SLpattern bit <i> = 1" << std::endl;
309 savestream <<
"# - must not have a hit if SLpattenr bit <i> = 0 " << std::endl;
311 savestream << print1dArray<unsigned long>(
"SLpatternMask",
SLpatternMask);
312 savestream << std::endl;
313 }
else {savestream <<
"SLpatternMask = [170]" << std::endl;}
314 savestream <<
"# precision used for the hardware simulation " << std::endl;
316 savestream << print1dArray<unsigned>(
"precision",
precision);
317 savestream << std::endl;
318 }
else {savestream <<
"precision = [12, 8, 8, 12, 10, 10]" << std::endl;}
319 savestream <<
"# Set Addition Wire output mode, 0 for default mode, 1 for full hits case and 2 for selected hits case" <<
323 savestream << std::endl;
324 }
else {savestream <<
"AdditionWireMode = 0" << std::endl;}
326 "# Only used when AdditionWireMode != 0, if mode ==1 , InputPerSL can be 11 (only drift time) and 22 (drift time + ADC ); if mode ==2, InputPerSL can be 3 * n , n equal to the number of wire selected "
331 savestream << std::endl;
332 }
else {savestream <<
"AdditionInputPerSL = 0" << std::endl;}
341 std::stringstream savestream;
342 savestream << name <<
" " << (vecvec[0][0].isLocked() ?
"== " :
"= ") <<
"[";
343 bool outcomma =
false;
344 for (
auto x : vecvec) {
345 if (outcomma) {savestream <<
",";}
348 bool incomma =
false;
350 if (incomma) {savestream <<
",";}
356 savestream <<
"]" << std::endl;
357 return savestream.str();
363 std::stringstream savestream;
364 savestream << name <<
" " << (vecvec[0].isLocked() ?
"== " :
"= ") <<
"[";
365 bool incomma =
false;
366 for (
auto y : vecvec) {
367 if (incomma) {savestream <<
",";}
371 savestream <<
"]" << std::endl;
372 return savestream.str();
377 std::vector<std::vector<NNTParam<X>>> retarr;
378 std::string key = keyx;
380 key = key.substr(key.find(
"[") + 1, std::string::npos);
381 for (std::size_t ipos = 0; ipos != std::string::npos; ipos = key.find(
"[", ipos + 1)) {
382 std::string pairstr = key.substr(ipos + 1, key.find(
"]", ipos + 1) - ipos - 1);
383 std::vector<NNTParam<X>> newpair;
385 for (jpos = 0; jpos != std::string::npos; jpos = pairstr.find(
",", jpos)) {
386 if (!(jpos == 0)) {jpos++;}
387 newpair.push_back(
NNTParam<X>(std::stof(pairstr.substr(jpos, pairstr.find(
",") - jpos))));
388 if (locked) {newpair.back().lock();}
390 retarr.push_back(newpair);
398 std::string key = keyx;
400 std::string pairstr = key.substr(1, key.find(
"]", 1) - 1);
401 std::vector<NNTParam<X>> newpair;
403 for (jpos = 0; jpos != std::string::npos; jpos = pairstr.find(
",", jpos)) {
404 if (!(jpos == 0)) {jpos++;}
405 newpair.push_back(
NNTParam<X>(std::stof(pairstr.substr(jpos, pairstr.find(
",") - jpos))));
406 if (locked) {newpair.back().lock();}
Class to represent a complete set to describe a Neurotrigger.
std::vector< NNTParam< unsigned short > > maxHitsPerSL
Maximum number of hits in a single super layer for all networks.
std::vector< std::vector< NNTParam< float > > > invptRangeUse
Charge / Pt region for which MLP is used in 1/GeV for all networks.
std::vector< std::vector< NNTParam< float > > > thetaRangeUse
Theta region for which MLP is used in degree for all networks.
NNTParam< unsigned > AdditionWireMode
Flag for the addtional wire input usage: 0 for default, 1 selected additional wire,...
NNTParam< unsigned > nMLP
Number of networks.
std::vector< NNTParam< unsigned long > > SLpatternMask
Super layer pattern mask for which MLP is trained for all networks.
NNTParam< unsigned > AdditionInputPerSL
Number for the addtional wire input per SL.
std::vector< std::vector< NNTParam< float > > > nHidden
Number of nodes in each hidden layer for all networks or factor to multiply with number of inputs.
std::vector< std::vector< NNTParam< float > > > thetaRangeTrain
Theta region for which MLP is trained in degree for all networks.
bool checkarr(std::vector< std::vector< NNTParam< X > > > vec)
check, if a vector is already set.
NNTParam< unsigned > tMax
Maximal drift time, identical for all networks.
std::vector< NNTParam< X > > read1dArray(std::string keyx, bool locked)
fill the array from a given string that looks like: [1,2,3]
std::vector< NNTParam< unsigned long > > SLpattern
Super layer pattern for which MLP is trained for all networks.
std::string print2dArray(const std::string &name, std::vector< std::vector< NNTParam< X > > > vecvec)
this is a class for piping the output of a 2d array to a string with brackets
NNTParam< bool > rescaleTarget
flag to allow for target tracks lying out of the output range to be rescaled during training.
std::vector< std::vector< NNTParam< float > > > IDRanges
relative ID range of the relevant wire IDs of the track segments that are taken into consideration wh...
NNTParam< bool > multiplyHidden
If true, multiply nHidden with number of input nodes.
NNTParam< bool > targetTheta
train theta as output
NNTParam< unsigned > nOutput
number of output nodes
std::vector< std::vector< NNTParam< float > > > phiRangeUse
Phi region for which MLP is used in degree for all networks.
NNTParam< unsigned > ETOption
Determine, how the event time should be obtained.
NNTParam< bool > targetZ
train z as output
NNTParam< bool > cutSum
only used in the idhist module.
std::vector< std::vector< NNTParam< X > > > read2dArray(std::string keyx, bool locked)
fill the array from a given string that looks like: [[1,2],[3, 4]]
std::vector< std::vector< NNTParam< float > > > invptRangeTrain
Charge / Pt region for which MLP is trained in 1/GeV for all networks.
std::vector< std::vector< NNTParam< float > > > phiRangeTrain
Phi region for which MLP is trained in degree for all networks.
void loadconfigtxt(const std::string &filename)
load the configuration from a file
void saveconfigtxt(const std::string &filename)
save the configuration to a file
std::string print1dArray(const std::string &name, std::vector< NNTParam< X > > vecvec)
this is a class for piping the output of a 1d array to a string with brackets
NNTParam< double > relevantCut
only used in the idhist module.
NNTParam< unsigned > nInput
Network parameters.
std::vector< NNTParam< unsigned > > precision
precision used for the hardware simulation
std::vector< std::vector< NNTParam< float > > > outputScale
Output scale for all networks.
Abstract base class for different kinds of events.