9#include <alignment/GlobalTimeLine.h>
11#include <framework/core/PyObjConvUtils.h>
12#include <framework/database/EventDependency.h>
22 EventMetaData gotoNextChangeRunWise(TimeTable& timeTable,
int uid,
int& timeid)
24 auto& row = std::get<TableData>(timeTable).at(uid);
26 auto lastIntervalStartEvent = std::get<EventHeader>(timeTable).at(row.size() - 1);
28 if (timeid >=
int(row.size())) {
29 return lastIntervalStartEvent;
32 auto cell = row.at(timeid);
33 auto cellRun = std::get<RunHeader>(timeTable).at(timeid);
34 for (
long unsigned int iCol = timeid + 1; iCol < row.size(); ++iCol) {
35 if (row.at(iCol) != cell && std::get<RunHeader>(timeTable).at(iCol) != cellRun) {
37 return std::get<EventHeader>(timeTable).at(iCol);
41 timeid = row.size() - 1;
43 return lastIntervalStartEvent;
46 EventMetaData gotoNextChangeInRun(TimeTable& timeTable,
int uid,
int& timeid)
48 auto& row = std::get<TableData>(timeTable).at(uid);
49 auto cell = row.at(timeid);
50 auto cellRun = std::get<RunHeader>(timeTable).at(timeid);
51 for (
long unsigned int iCol = timeid + 1; iCol < row.size(); ++iCol) {
52 if (std::get<RunHeader>(timeTable).at(iCol) != cellRun) {
54 return std::get<EventHeader>(timeTable).at(iCol - 1);
56 if (row.at(iCol) != cell) {
58 return std::get<EventHeader>(timeTable).at(iCol);
61 return std::get<EventHeader>(timeTable).at(timeid);
64 PayloadsTable TimeIdsTable2PayloadsTable(TimeTable& timeTable,
const GlobalParamVector& vector)
66 PayloadsTable payloadsTable;
68 for (
auto& uid_obj : vector.getGlobalParamSets()) {
69 auto uid = uid_obj.first;
70 auto& obj = uid_obj.second;
72 payloadsTable[uid] = {};
74 if (std::get<TableData>(timeTable).find(uid) == std::get<TableData>(timeTable).end()) {
75 auto firstEvent = std::get<EventHeader>(timeTable).at(0);
78 auto iov = IntervalOfValidity(firstEvent.getExperiment(), firstEvent.getRun(), -1, -1);
79 auto objCopy = std::shared_ptr<GlobalParamSetAccess>(obj->clone());
80 payloadsTable[uid].push_back({ iov, {{firstEvent, objCopy}} });
86 for (; iCol < int(std::get<EventHeader>(timeTable).size()); ++iCol) {
87 auto event = std::get<EventHeader>(timeTable).at(iCol);
88 auto exprun = std::get<RunHeader>(timeTable).at(iCol);
89 auto exp = exprun.first;
90 auto run = exprun.second;
94 auto objCopy = std::shared_ptr<GlobalParamSetAccess>(obj->clone());
95 IntraIoVPayloads intraRunEntries;
96 intraRunEntries.push_back({event, objCopy});
98 auto lastEvent = event;
99 for (; iCol < int(std::get<EventHeader>(timeTable).size());) {
100 auto nextEvent = gotoNextChangeInRun(timeTable, uid, iCol);
101 if (nextEvent != lastEvent) {
102 auto objIntraRunCopy = std::shared_ptr<GlobalParamSetAccess>(obj->clone());
103 intraRunEntries.push_back({nextEvent, objIntraRunCopy});
104 lastEvent = nextEvent;
111 auto endEvent = gotoNextChangeRunWise(timeTable, uid, iCol);
112 int endExp = endEvent.getExperiment();
114 int endRun = std::max(0, endEvent.getRun() - 1);
116 if (iCol ==
static_cast<int>(std::get<EventHeader>(timeTable).size()) - 1) {
121 payloadsTable[uid].push_back({IntervalOfValidity(exp, run, endExp, endRun), intraRunEntries});
127 return payloadsTable;
130 TimeTable makeInitialTimeTable(std::vector< EventMetaData > events, GlobalLabel& label)
133 std::vector<int> nullRow(events.size(), 0);
136 std::get<EventHeader>(table) = events;
140 for (
auto event : events) {
141 runs.push_back({
event.getExperiment(), event.getRun()});
143 std::get<RunHeader>(table) = runs;
145 for (
auto& eidpid_intervals : label.getTimeIntervals()) {
146 auto uid = GlobalLabel(eidpid_intervals.first).getUniqueId();
147 if (std::get<TableData>(table).find(uid) == std::get<TableData>(table).end()) {
148 std::get<TableData>(table)[uid] = nullRow;
150 unsigned int lastTime = 0;
151 for (
long unsigned int timeid = 0; timeid < events.size(); ++timeid) {
152 if (lastTime != eidpid_intervals.second.get(timeid)) {
153 std::get<TableData>(table)[uid][timeid] = 1;
162 void finalizeTimeTable(TimeTable& table)
164 for (
auto& row : std::get<TableData>(table)) {
165 auto& cells = row.second;
168 for (
long unsigned int iCell = 0; iCell < cells.size(); ++iCell) {
169 auto cell = cells.at(iCell);
172 B2FATAL(
"First cell (index 0) has to be zero (time id for const objects or 1st instance of time-dep objects) for each row.");
176 if (cell != 0 && cell != 1) {
177 B2FATAL(
"In initial time table, only cells with 0 (=no change of object at beginning of cell) or 1 (object can change at beginning of this cell) are allowed");
183 cells.at(iCell) = currIndex;
188 std::pair< EventMetaData, std::shared_ptr< GlobalParamSetAccess > > getPayloadByContinuousIndex(PayloadsTable& payloadsTable,
189 int uid,
long unsigned int index)
191 auto& row = payloadsTable.at(uid);
193 long unsigned int currentIndex = 0;
194 for (
long unsigned int iIovBlock = 0; iIovBlock < row.size(); ++iIovBlock) {
195 if (currentIndex + row.at(iIovBlock).second.size() > index) {
196 return row.at(iIovBlock).second.at(index - currentIndex);
198 currentIndex += row.at(iIovBlock).second.size();
201 return {EventMetaData(), {}};
204 int getContinuousIndexByTimeID(
const TimeTable& timeTable,
int uid,
int timeid)
208 if (std::get<TableData>(timeTable).find(uid) == std::get<TableData>(timeTable).end())
210 if (timeid >=
int(std::get<TableData>(timeTable).at(uid).size()))
211 return std::get<TableData>(timeTable).at(uid).size() - 1;
213 auto cIndex = std::get<TableData>(timeTable).at(uid)[timeid];
220 const GlobalParamVector& vector) : timeTable(makeInitialTimeTable(events, label))
229 std::map<std::tuple<int, int, int>, std::vector<std::shared_ptr<GlobalParamSetAccess>>> eventPayloads{};
231 for (
auto& iovBlock : row.second) {
232 for (
auto& payload : iovBlock.second) {
233 auto eventTuple = std::make_tuple((
int)payload.first.getExperiment(), (
int)payload.first.getRun(), (
int)payload.first.getEvent());
234 auto iter_and_inserted = eventPayloads.insert(
235 {eventTuple, std::vector<std::shared_ptr<GlobalParamSetAccess>>()}
237 iter_and_inserted.first->second.push_back(payload.second);
241 for (
auto event_payloads : eventPayloads) {
242 auto event =
EventMetaData(std::get<2>(event_payloads.first), std::get<1>(event_payloads.first), std::get<0>(event_payloads.first));
245 for (
auto& payload : event_payloads.second) {
246 payload->loadFromDBObjPtr();
253 auto timeid = label.getTimeId();
254 auto eov = label.getEndOfValidity();
255 auto uid = label.getUniqueId();
257 std::set<int> payloadIndices;
260 for (
int i = timeid; i < std::min(eov + 1, int(std::get<EventHeader>(
timeTable).size())); ++i) {
261 payloadIndices.insert(getContinuousIndexByTimeID(
timeTable, uid, i));
264 for (
auto payloadIndex : payloadIndices) {
265 auto payload = getPayloadByContinuousIndex(
payloadsTable, label.getUniqueId(), payloadIndex).second;
269 payload->setGlobalParam(correction, label.getElementId(), label.getParameterId());
271 payload->updateGlobalParam(correction, label.getElementId(), label.getParameterId());
280 std::vector<std::pair<IntervalOfValidity, TObject*>> result;
283 for (
auto& iovBlock : row.second) {
284 auto iov = iovBlock.first;
285 auto obj = iovBlock.second.at(0).second->releaseObject();
288 if (iovBlock.second.size() == 1) {
290 result.push_back({iov, obj});
301 for (
long unsigned int iObj = 1; iObj < iovBlock.second.size(); ++iObj) {
302 auto nextEvent = iovBlock.second.at(iObj).first.getEvent();
303 auto nextObj = iovBlock.second.at(iObj).second->releaseObject();
306 payloads->add(nextEvent, nextObj);
309 result.push_back({iov, payloads});
316 std::vector< EventMetaData > setupTimedepGlobalLabels(PyObject* config)
318 boost::python::handle<> handle(boost::python::borrowed(config));
319 boost::python::list configList(handle);
321 std::vector< std::tuple< std::vector< int >, std::vector< std::tuple< int, int, int > > > >());
322 return setupTimedepGlobalLabels(newConfig);
327 std::vector<EventMetaData> setupTimedepGlobalLabels(
328 std::vector< std::tuple< std::vector< int >, std::vector< std::tuple< int, int, int > > > >& config)
330 std::vector< std::tuple< std::set< int >, std::set< std::tuple< int, int, int > > > > myConfig = {};
331 std::set<std::tuple<int, int, int>> events;
332 for (
auto& params_events : config) {
333 auto myRow = std::make_tuple(std::set<int>(), std::set<std::tuple< int, int, int>>());
335 for (
auto& param : std::get<0>(params_events))
336 std::get<0>(myRow).insert(param);
337 for (
auto& event : std::get<1>(params_events)) {
340 std::get<1>(myRow).insert(std::make_tuple(std::get<2>(event), std::get<1>(event), std::get<0>(event)));
343 for (
auto& event : std::get<1>(params_events)) {
344 int eventNum = std::get<0>(event);
345 int runNum = std::get<1>(event);
346 int expNum = std::get<2>(event);
349 auto emd = std::make_tuple(expNum, runNum, eventNum);
358 auto firstEventThisRun = std::make_tuple(expNum, runNum, 0);
359 auto firstEventNextRun = std::make_tuple(expNum, runNum + 1, 0);
361 events.insert(firstEventThisRun);
362 events.insert(firstEventNextRun);
364 std::get<1>(myRow).insert(firstEventThisRun);
365 std::get<1>(myRow).insert(firstEventNextRun);
368 myConfig.push_back(myRow);
371 std::vector<EventMetaData> eventsVect;
372 std::map<std::tuple<int, int, int>,
int> eventIndices;
375 for (
auto& event : events) {
377 eventIndices[event] = eventsVect.size();
378 eventsVect.push_back(EventMetaData(std::get<2>(event), std::get<1>(event), std::get<0>(event)));
383 for (
auto& params_events : myConfig) {
384 for (
auto& param : std::get<0>(params_events)) {
385 GlobalLabel label(param);
387 for (
auto& event : std::get<1>(params_events)) {
388 auto eventIndex = eventIndices[event];
390 label.registerTimeDependent(eventIndex);
Class for handling changing conditions as a function of event number.
Class to convert to/from global labels for Millepede II to/from detector & parameter identificators.
static void clearTimeDependentParamaters()
Forget all previously registered time dependent parameters.
The central user class to manipulate any global constant in any DB object Used to retrieve global par...
GlobalParamTimeLine(const std::vector< EventMetaData > &events, GlobalLabel &label, const GlobalParamVector &vector)
Constructor.
PayloadsTable payloadsTable
Table with payloads.
std::vector< std::pair< IntervalOfValidity, TObject * > > releaseObjects()
Release all the objects (you become the owner!) for DB storage.
void loadFromDB()
Load every single payload with the content in database at its corresponding event (when it should sta...
void updateGlobalParam(GlobalLabel label, double correction, bool resetParam=false)
Add a correction to any payload's parameter in the timeline.
TimeTable timeTable
The final TimeTable with payload indices.
static DBStore & Instance()
Instance of a singleton DBStore.
void updateEvent()
Updates all intra-run dependent objects.
void update()
Updates all objects that are outside their interval of validity.
Scalar convertPythonObject(const boost::python::object &pyObject, Scalar)
Convert from Python to given type.
Abstract base class for different kinds of events.