Hyperiso 1.0.3
Modular flavour-physics calculations, Wilson coefficients and statistical inference
Loading...
Searching...
No Matches
Block.cpp
Go to the documentation of this file.
1#include "Block.h"
2#include "SourcesView.h"
3
4void Block::addObserver(std::shared_ptr<Block> observer) {
5 auto it = std::find_if(observers.begin(), observers.end(),
6 [&](const std::shared_ptr<Block>& p){ return p.get() == observer.get(); });
7 if (it == observers.end()) observers.push_back(observer);
8}
9
10
11void Block::removeObserver(std::shared_ptr<Block> observer) {
12 auto it = std::find_if(observers.begin(), observers.end(),
13 [&](const std::shared_ptr<Block>& p){ return p.get() == observer.get(); });
14 if (it != observers.end()) observers.erase(it);
15}
16
18 for (size_t i = 0; i < observers.size(); ++i) {
19 auto& observer = observers[i];
20 if (!observer) continue;
21 LOG_DEBUG("Notifying observer", observer->blockname, "from source block", blockname);
22 observer->update();
23 }
24 observers.erase(std::remove(observers.begin(), observers.end(), nullptr), observers.end());
25}
26
27std::vector<std::shared_ptr<Block>> Block::getObservers() const {
28 return observers;
29}
30
32 LOG_DEBUG("In Block::update");
33 for (auto& [_, param] : this->items) {
34 param->update();
35 }
36}
37
39 for (auto& [_, param] : this->items) {
40 param->freeze();
41 }
42}
43
45 for (auto& [_, param] : this->items) {
46 param->unfreeze();
47 }
48}
49
50Block::Block(std::shared_ptr<Block> other) {
51 this->copy(other);
52}
53
54std::shared_ptr<Parameter> Block::retrieve(const LhaID& id) {
55 this->ensure_up_to_date();
56
57 if (!this->contains(id)) {
58 LOG_ERROR("KeyError", "Block", this->blockname, "doesn't contain parameter",
59 id.to_string(), ". Available keys are", std::make_shared<Block>(*this));
60 }
61 return this->items.at(id);
62}
63
64void Block::store(const LhaID& id, std::shared_ptr<Parameter> param) {
65 if (this->contains(id)) {
66 LOG_DEBUG("Block", blockname, "already contains a parameter with id", id.to_string());
67 } else {
68 auto w = self_weak();
69 if (!w.expired()) param->set_owner_block(w);
70
71 this->items.emplace(id, std::move(param));
72 }
73}
74
75void Block::erase_local(const LhaID& id) {
76 this->items.erase(id);
77}
78
79void Block::assign(const LhaID& key, std::shared_ptr<Parameter> param) {
80 if (!this->contains(key)) {
81 LOG_ERROR("KeyError", "Cannot update non-existing parameter", key.to_string(), "in block", this->blockname);
82 }
83 auto& dst = this->items.at(key);
84 dst->overwrite_payload_from(*param);
85
86 dst->notifyObservers();
87
88}
89
90void Block::assign(const LhaID& key, scalar_t value) {
91 if (!this->contains(key)) {
92 LOG_ERROR("KeyError", "Cannot update non-existing parameter", key.to_string(), "in block", this->blockname);
93 }
94 auto& p = this->items.at(key);
95 p->set_expected(value);
96}
97
98void Block::store_or_assign(const LhaID& id, std::shared_ptr<Parameter> param) {
99 if (!contains(id)) {
100 store(id, std::move(param));
101 } else {
102 assign(id, std::move(param));
103 }
104}
105
106bool Block::contains(const LhaID& id) const {
107
108 const_cast<Block*>(this)->ensure_up_to_date();
109
110 return this->items.contains(id);
111}
112
113void Block::remove(const LhaID& id) {
114 if (!this->items.contains(id)) {
115 LOG_ERROR("Cannot remove non-existing parameter", id, "in block", blockname);
116 }
117 this->items.at(id)->clear_below();
118 this->items.erase(id);
119
120 auto dependents = std::exchange(observers, {});
121 for (auto& obs : dependents) {
122 if (obs) obs->destroy();
123 }
124}
125
127 for (auto& [_, param] : items) {
128 param->set_owner(type);
129 }
130}
131
132std::unordered_set<LhaID> Block::getAllIDs() {
134 return get_keys(this->items);
135}
136
137const std::map<LhaID, std::shared_ptr<Parameter>>& Block::getItems() {
139 return this->items;
140};
141
142void Block::copy(std::shared_ptr<Block> other) {
143 this->items = other->getItems();
144 this->blockname = other->blockname;
145 if (other->has_scale()) this->set_scale(other->get_scale());
146
147 auto w = self_weak();
148 if (!w.expired()) {
149 for (auto& [id, p] : items) if (p) p->set_owner_block(w);
150 }
151}
152
153std::shared_ptr<Block> Block::deep_clone_plain() const {
154 auto clone = std::make_shared<Block>();
155 clone->blockname = this->blockname;
156 if (this->scale.has_value()) {
157 clone->scale = this->scale;
158 }
159
160 for (const auto& [id, param] : this->items) {
161 if (!param) {
162 continue;
163 }
164 clone->items.emplace(id, std::make_shared<Parameter>(*param));
165 }
166
167 return clone;
168}
169
171 for (auto& param: this->items) {
172 param.second->clear_above();
173 }
174}
175
177 std::vector<std::shared_ptr<Parameter>> snapshot;
178 snapshot.reserve(items.size());
179 for (auto& kv : items) snapshot.push_back(kv.second);
180
181 for (auto& p : snapshot) {
182 if (p) p->clear_below();
183 }
184}
185
186
188 return this->scale.has_value();
189}
190
191void Block::set_scale(double scale) {
192 if (this->has_scale())
193 LOG_ERROR("LogicError", "Cannot set scale of a block which already has one.");
194
195 this->scale.emplace(scale);
196}
197
199 if (!this->has_scale())
200 LOG_ERROR("LogicError", "Scale for the block ", this->get_name() ," has not been set, cannot retrieve it.");
201
202 return this->scale.value_or(0.0);
203}
204
206 auto dependents = std::exchange(observers, {});
207
208 clear_below();
209 items.clear();
210
211 for (auto& obs : dependents) {
212 if (obs) obs->destroy();
213 }
214}
215
216std::unordered_map<std::string, std::shared_ptr<Block>> Block::get_source_blocks() const {
217 return {};
218}
219
221 auto me_base = shared_from_this();
222 auto me_dep = std::static_pointer_cast<DependentBlock>(me_base);
223 self = me_dep;
224
225 for (auto& [_, src] : sourceBlocks) src->addObserver(me_base);
226}
227
229 this->frozen = true;
231}
232
233
235 this->frozen = false;
236
238
239 if (this->update_at_unfreeze) {
240 this->update();
241 this->update_at_unfreeze = false;
242 }
243}
244
246 LOG_DEBUG("Destruct dependentBlock at", self.lock().get());
247 if (auto me_dep = self.lock()) {
248 auto me_base = std::static_pointer_cast<Block>(me_dep);
249 for (auto& [_, src] : sourceBlocks) {
250 src->removeObserver(me_base);
251 }
252 }
253}
254
255
256void DependentBlock::assign(const LhaID& key, std::shared_ptr<Parameter> param)
257{
258 if (!this->contains(key)) {
259 LOG_ERROR("KeyError", "Cannot update non-existing parameter", key.to_string(), "in block", this->blockname);
260 }
261
262 auto& dst = this->items.at(key);
263 dst->overwrite_payload_from(*param);
264}
265
266
267
268
269void DependentBlock::assign(const LhaID &key, double value) {
270 if (!this->contains(key)) {
271 LOG_ERROR("KeyError", "Cannot update non-existing parameter", key.to_string(), "in block", this->blockname);
272 }
273 this->items.at(key)->set_expected(value);
274}
275
276std::unordered_map<std::string, std::shared_ptr<Block>> DependentBlock::get_source_blocks() const {
277 return this->sourceBlocks;
278}
279
281 if (auto me = self.lock()) {
282 for (auto& [_, block] : sourceBlocks) {
283 block->removeObserver(me);
284 }
285 }
286}
287
289 this->clear_above();
290
291 if (observers.empty()) return;
292
293 auto snapshot = observers;
294 for (auto& obs : snapshot) {
295 if (obs) obs->clear_below();
296 }
297}
298
299bool DependentBlock::dependsOn(const std::string& blockName) {
300 return sourceBlocks.contains(blockName) && sourceBlocks.at(blockName) != nullptr;
301}
302
304 LOG_DEBUG("destroying (depblock) :", this->blockname);
305
306 auto dependents = std::exchange(observers, {});
307
308 clear_above();
309
310 for (auto& kv : items) {
311 kv.second->clear_below();
312 }
313 items.clear();
314
315 for (auto& obs : dependents) {
316 if (obs) obs->destroy();
317 }
318}
319
321 if (dependency_detached) return;
322
324
325 clear_above();
326
327 for (auto& [_, p] : items) {
328 if (auto dp = std::dynamic_pointer_cast<DependentParameter>(p)) {
329 dp->detach();
330 }
331 }
332
333 sourceBlocks.clear();
334 recalculateLambda = {};
335 dirty = false;
336 frozen = false;
337 update_at_unfreeze = false;
338 dependency_detached = true;
339
341}
342
344 if (!dependency_detached) return;
345
346 sourceBlocks = saved_sourceBlocks;
347 recalculateLambda = saved_recalculateLambda;
348
349 for (auto& [_, p] : items) {
350 if (auto dp = std::dynamic_pointer_cast<DependentParameter>(p)) {
351 dp->reattach();
352 }
353 }
354
355 if (auto me = self.lock()) {
356 for (auto& [_, src] : sourceBlocks) {
357 if (src) src->addObserver(me);
358 }
359 }
360
361 dirty = true;
362 frozen = false;
363 update_at_unfreeze = false;
364 dependency_detached = false;
365
367}
368
370 if (dirty) return;
371 dirty = true;
372
373 for (auto& obs : observers) {
374 if (auto dep = std::dynamic_pointer_cast<DependentBlock>(obs)) {
375 dep->mark_dirty();
376 }
377 }
378
379 for (auto& [_, p] : items) {
380 if (p) p->notifyParamObserversOnly();
381 }
382}
383
385 if (frozen) { update_at_unfreeze = true; return; }
386 mark_dirty();
387}
388
389void DependentBlock::ensure_up_to_date_impl() {
390 if (frozen) return;
391 if (!dirty) return;
392
393 for (auto& [name, src] : sourceBlocks) {
394 if (!src) continue;
395 if (auto depSrc = std::dynamic_pointer_cast<DependentBlock>(src)) {
396 depSrc->ensure_up_to_date();
397 }
398 }
399
400 dirty = false;
401
402 if (!recalculateLambda) LOG_ERROR("Error", "DependentBlock has no recalculateLambda");
403 auto me_dep = std::static_pointer_cast<DependentBlock>(shared_from_this());
404 recalculateLambda(BlockSrc(this->sourceBlocks, this->blockname), me_dep);
405
406 for (auto& [_, p] : items) {
407 if (p) p->notifyParamObserversOnly();
408 }
409
411}
412
413std::ostream &operator<<(std::ostream &os, std::shared_ptr<Block> ba) {
414 os << "Block " << ba->get_name() << ":\n";
415 for (auto &[id, val] : ba->getItems()) {
416 os << '\t' << id << ": " << val->get_val() << '\n';
417 }
418 os << '\n';
419 return os;
420}
std::ostream & operator<<(std::ostream &os, std::shared_ptr< Block > ba)
Definition Block.cpp:413
Defines classes used to store parameters and to build derived/dependent parameter blocks.
ParameterType
#define LOG_ERROR(type,...)
Macro for logging error messages and terminating the application.
Definition Logger.h:41
#define LOG_DEBUG(...)
Macro for logging debug messages.
Definition Logger.h:45
std::string to_string(const LhaID &id)
Convenience stringification for LhaID.
Definition SourceView.cpp:9
std::unordered_set< T > get_keys(const std::map< T, U > &map)
Extracts the key set from a std::map into an unordered_set.
Definition Utils.h:108
Lightweight view over a set of source blocks.
Definition SourcesView.h:71
Definition Block.h:73
virtual void freeze()
Freezes all parameters contained in the block.
Definition Block.cpp:38
double get_scale()
Returns the block-wide scale.
Definition Block.cpp:198
void addObserver(std::shared_ptr< Block > observer)
Adds a block observer if not already present.
Definition Block.cpp:4
virtual void update()
Updates the block.
Definition Block.cpp:31
std::unordered_set< LhaID > getAllIDs()
Returns the set of all parameter ids stored in the block.
Definition Block.cpp:132
std::map< LhaID, std::shared_ptr< Parameter > > items
List of observing blocks notified through notifyObservers().
Definition Block.h:438
virtual void unfreeze()
Unfreezes all parameters contained in the block.
Definition Block.cpp:44
void store_or_assign(const LhaID &key, std::shared_ptr< Parameter > param) override
Stores a parameter if absent, otherwise assigns into the existing one.
Definition Block.cpp:98
void removeObserver(std::shared_ptr< Block > observer)
Removes a previously registered observer block.
Definition Block.cpp:11
virtual void destroy()
Destroys the block and its downstream block dependencies.
Definition Block.cpp:205
void set_owner(ParameterType type)
Sets the owner ParameterType on all contained parameters.
Definition Block.cpp:126
void notifyObservers()
Notifies all observer blocks that this block has changed.
Definition Block.cpp:17
std::shared_ptr< Block > deep_clone_plain() const
Deep-copies this block as a plain independent block.
Definition Block.cpp:153
void erase_local(const LhaID &id)
Erases an entry from the local storage map only.
Definition Block.cpp:75
void assign(const LhaID &key, std::shared_ptr< Parameter > param) override
Replaces the payload of an existing parameter from another parameter object.
Definition Block.cpp:79
virtual void clear_below()
Clears parameter dependencies below this block.
Definition Block.cpp:176
void set_scale(double scale)
Sets the block-wide scale.
Definition Block.cpp:191
BlockName blockname
Name of the block (e.g. "SMINPUTS", "MASS", "FWCOEF"...)
Definition Block.h:76
std::vector< std::shared_ptr< Block > > observers
Definition Block.h:437
bool has_scale()
Returns whether the block has an associated scale.
Definition Block.cpp:187
Block()=default
Default constructor.
virtual void clear_above()
Clears parameter dependencies above this block.
Definition Block.cpp:170
void remove(const LhaID &key) override
Removes a parameter and clears its downstream dependency subtree.
Definition Block.cpp:113
std::optional< double > scale
Internal storage of parameters indexed by LHA id.
Definition Block.h:439
virtual std::unordered_map< std::string, std::shared_ptr< Block > > get_source_blocks() const
Returns the source blocks of this block.
Definition Block.cpp:216
virtual void ensure_up_to_date()
Ensures that the block content is up to date.
Definition Block.h:391
void copy(std::shared_ptr< Block > other)
Copies the content and metadata from another block.
Definition Block.cpp:142
bool contains(const LhaID &key) const override
Checks whether the block contains a parameter with the given id.
Definition Block.cpp:106
void store(const LhaID &id, std::shared_ptr< Parameter > param) override
Stores a new parameter under the given LHA id.
Definition Block.cpp:64
std::weak_ptr< Block > self_weak()
Optional explicit self-reference used to rebind owner_block on contained parameters.
Definition Block.h:453
const std::map< LhaID, std::shared_ptr< Parameter > > & getItems()
Returns the internal parameter map.
Definition Block.cpp:137
std::shared_ptr< Parameter > retrieve(const LhaID &id) override
Retrieves a stored parameter by id.
Definition Block.cpp:54
std::vector< std::shared_ptr< Block > > getObservers() const
Returns the current list of observer blocks.
Definition Block.cpp:27
BlockName get_name() const
Returns the name of the block.
Definition Block.h:102
void clear_below() override
Clears downstream block dependencies.
Definition Block.cpp:288
std::unordered_map< std::string, std::shared_ptr< Block > > get_source_blocks() const override
Returns the map of source blocks for this dependent block.
Definition Block.cpp:276
void destroy() override
Destroys this dependent block and its downstream block dependencies.
Definition Block.cpp:303
void mark_dirty()
Marks this block dirty and propagates the dirty state downstream.
Definition Block.cpp:369
void update() override
Marks the block as dirty.
Definition Block.cpp:384
void detach()
Temporarily detaches this block from its dependency graph.
Definition Block.cpp:320
bool dependsOn(const std::string &blockName)
Checks whether this dependent block uses a given source block name.
Definition Block.cpp:299
~DependentBlock()
Destructor.
Definition Block.cpp:245
void freeze() override
Freezes the block and all contained parameters.
Definition Block.cpp:228
void unfreeze() override
Unfreezes the block and contained parameters.
Definition Block.cpp:234
void init() override
Initializes the dependency graph for this block.
Definition Block.cpp:220
void assign(const LhaID &key, std::shared_ptr< Parameter > param)
Overwrites the payload of a local parameter without triggering block-level notification.
Definition Block.cpp:256
void ensure_up_to_date() override
Ensures this dependent block is up to date.
Definition Block.h:656
void reattach()
Reattaches a previously detached dependent block.
Definition Block.cpp:343
void clear_above() override
Clears upstream block dependencies.
Definition Block.cpp:280
Represents an identifier of a LHA element, possibly containing several sub-ids.
Definition LhaID.h:56
std::string to_string() const
Returns the canonical string representation of this LhaID.
Definition LhaID.cpp:19