@@ -21,18 +21,21 @@ template <class MainModel, class... ComponentType>
21
21
class JobDispatchAdapter <MainModel, ComponentList<ComponentType...>>
22
22
: public JobDispatchInterface<JobDispatchAdapter<MainModel, ComponentList<ComponentType...>>> {
23
23
public:
24
- JobDispatchAdapter (MainModel& model, std::reference_wrapper<MainModelOptions const > options)
25
- : model_{std::make_unique<MainModel>(model)}, options_{options} {}
24
+ JobDispatchAdapter (std::reference_wrapper<MainModel> model_reference,
25
+ std::reference_wrapper<MainModelOptions const > options)
26
+ : model_reference_{model_reference}, options_{options} {}
26
27
JobDispatchAdapter (JobDispatchAdapter const & other)
27
- : model_{std::make_unique<MainModel>(*other.model_ )},
28
+ : model_copy_{std::make_unique<MainModel>(other.model_reference_ .get ())},
29
+ model_reference_{std::ref (*model_copy_)},
28
30
options_{std::ref (other.options_ )},
29
31
components_to_update_{other.components_to_update_ },
30
32
update_independence_{other.update_independence_ },
31
33
independence_flags_{other.independence_flags_ },
32
34
all_scenarios_sequence_{other.all_scenarios_sequence_ } {}
33
35
JobDispatchAdapter& operator =(JobDispatchAdapter const & other) {
34
36
if (this != &other) {
35
- model_ = std::make_unique<MainModel>(*other.model_ );
37
+ model_copy_ = std::make_unique<MainModel>(other.model_reference_ .get ());
38
+ model_reference_ = std::ref (*model_copy_);
36
39
options_ = std::ref (other.options_ );
37
40
components_to_update_ = other.components_to_update_ ;
38
41
update_independence_ = other.update_independence_ ;
@@ -42,15 +45,17 @@ class JobDispatchAdapter<MainModel, ComponentList<ComponentType...>>
42
45
return *this ;
43
46
}
44
47
JobDispatchAdapter (JobDispatchAdapter&& other) noexcept
45
- : model_{std::move (other.model_ )},
48
+ : model_copy_{std::move (other.model_copy_ )},
49
+ model_reference_{model_copy_ ? std::ref (*model_copy_) : std::move (other.model_reference_ )},
46
50
options_{other.options_ },
47
51
components_to_update_{std::move (other.components_to_update_ )},
48
52
update_independence_{std::move (other.update_independence_ )},
49
53
independence_flags_{std::move (other.independence_flags_ )},
50
54
all_scenarios_sequence_{std::move (other.all_scenarios_sequence_ )} {}
51
55
JobDispatchAdapter& operator =(JobDispatchAdapter&& other) noexcept {
52
56
if (this != &other) {
53
- model_ = std::move (other.model_ );
57
+ model_copy_ = std::move (other.model_copy_ );
58
+ model_reference_ = model_copy_ ? std::ref (*model_copy_) : std::move (other.model_reference_ );
54
59
options_ = other.options_ ;
55
60
components_to_update_ = std::move (other.components_to_update_ );
56
61
update_independence_ = std::move (other.update_independence_ );
@@ -59,15 +64,16 @@ class JobDispatchAdapter<MainModel, ComponentList<ComponentType...>>
59
64
}
60
65
return *this ;
61
66
}
62
- ~JobDispatchAdapter () { model_ .reset (); }
67
+ ~JobDispatchAdapter () { model_copy_ .reset (); }
63
68
64
69
private:
65
70
// Grant the CRTP base (JobDispatchInterface<JobDispatchAdapter>) access to
66
71
// JobDispatchAdapter's private members. This allows the base class template
67
72
// to call derived-class implementation details as part of the CRTP pattern.
68
73
friend class JobDispatchInterface <JobDispatchAdapter>;
69
74
70
- std::unique_ptr<MainModel> model_;
75
+ std::unique_ptr<MainModel> model_copy_;
76
+ std::reference_wrapper<MainModel> model_reference_;
71
77
std::reference_wrapper<MainModelOptions const > options_;
72
78
73
79
main_core::utils::ComponentFlags<ComponentType...> components_to_update_{};
@@ -80,18 +86,19 @@ class JobDispatchAdapter<MainModel, ComponentList<ComponentType...>>
80
86
std::mutex calculation_info_mutex_;
81
87
82
88
void calculate_impl (MutableDataset const & result_data, Idx scenario_idx) const {
83
- MainModel::calculator (options_.get (), *model_, result_data.get_individual_scenario (scenario_idx), false );
89
+ MainModel::calculator (options_.get (), model_reference_.get (), result_data.get_individual_scenario (scenario_idx),
90
+ false );
84
91
}
85
92
86
93
void cache_calculate_impl () const {
87
94
// calculate once to cache topology, ignore results, all math solvers are initialized
88
95
try {
89
- MainModel::calculator (options_.get (), *model_ ,
96
+ MainModel::calculator (options_.get (), model_reference_. get () ,
90
97
{
91
98
false ,
92
99
1 ,
93
100
" sym_output" ,
94
- model_-> meta_data (),
101
+ model_reference_. get (). meta_data (),
95
102
},
96
103
true );
97
104
} catch (SparseMatrixError const &) { // NOLINT(bugprone-empty-catch) // NOSONAR
@@ -104,33 +111,35 @@ class JobDispatchAdapter<MainModel, ComponentList<ComponentType...>>
104
111
void prepare_job_dispatch_impl (ConstDataset const & update_data) {
105
112
// cache component update order where possible.
106
113
// the order for a cacheable (independent) component by definition is the same across all scenarios
107
- components_to_update_ = model_-> get_components_to_update (update_data);
108
- update_independence_ =
109
- main_core::update::independence::check_update_independence<ComponentType...>(model_-> state (), update_data);
114
+ components_to_update_ = model_reference_. get (). get_components_to_update (update_data);
115
+ update_independence_ = main_core::update::independence::check_update_independence<ComponentType...>(
116
+ model_reference_. get (). state (), update_data);
110
117
std::ranges::transform (update_independence_, independence_flags_.begin (),
111
118
[](auto const & comp) { return comp.is_independent (); });
112
119
all_scenarios_sequence_ = std::make_shared<main_core::utils::SequenceIdx<ComponentType...>>(
113
120
main_core::update::get_all_sequence_idx_map<ComponentType...>(
114
- model_-> state (), update_data, 0 , components_to_update_, update_independence_, false ));
121
+ model_reference_. get (). state (), update_data, 0 , components_to_update_, update_independence_, false ));
115
122
}
116
123
117
124
void setup_impl (ConstDataset const & update_data, Idx scenario_idx) {
118
125
current_scenario_sequence_cache_ = main_core::update::get_all_sequence_idx_map<ComponentType...>(
119
- model_->state (), update_data, scenario_idx, components_to_update_, update_independence_, true );
126
+ model_reference_.get ().state (), update_data, scenario_idx, components_to_update_, update_independence_,
127
+ true );
120
128
auto const current_scenario_sequence = get_current_scenario_sequence_view_ ();
121
- model_->template update_components <cached_update_t >(update_data, scenario_idx, current_scenario_sequence);
129
+ model_reference_.get ().template update_components <cached_update_t >(update_data, scenario_idx,
130
+ current_scenario_sequence);
122
131
}
123
132
124
133
void winddown_impl () {
125
- model_-> restore_components (get_current_scenario_sequence_view_ ());
134
+ model_reference_. get (). restore_components (get_current_scenario_sequence_view_ ());
126
135
std::ranges::for_each (current_scenario_sequence_cache_, [](auto & comp_seq_idx) { comp_seq_idx.clear (); });
127
136
}
128
137
129
- CalculationInfo get_calculation_info_impl () const { return model_-> calculation_info (); }
138
+ CalculationInfo get_calculation_info_impl () const { return model_reference_. get (). calculation_info (); }
130
139
131
140
void thread_safe_add_calculation_info_impl (CalculationInfo const & info) {
132
141
std::lock_guard const lock{calculation_info_mutex_};
133
- model_-> merge_calculation_info (info);
142
+ model_reference_. get (). merge_calculation_info (info);
134
143
}
135
144
136
145
auto get_current_scenario_sequence_view_ () const {
0 commit comments