31 std::vector<std::string> &bankEntryNames, H5::H5File &h5file, std::shared_ptr<NexusLoader> loader,
32 std::vector<int> &workspaceIndices, std::vector<SpectraProcessingData> &processingDatas,
34 const std::map<Mantid::Types::Core::DateAndTime, int> &splitterMap,
35 std::shared_ptr<std::vector<Types::Core::DateAndTime>> pulse_times, std::shared_ptr<API::Progress> &progress)
36 :
ProcessBankTaskBase(bankEntryNames, loader, calibFactory), m_h5file(h5file), m_workspaceIndices(workspaceIndices),
37 m_processingDatas(processingDatas), m_events_per_chunk(events_per_chunk), m_splitterMap(splitterMap),
38 m_grainsize_event(grainsize_event), m_pulse_times(pulse_times), m_progress(progress) {}
41 auto entry =
m_h5file.openGroup(
"entry");
42 for (
size_t bank_index = range.begin(); bank_index < range.end(); ++bank_index) {
52 auto event_group = entry.openGroup(
bankName);
56 const int64_t total_events =
static_cast<size_t>(tof_SDS.getSpace().getSelectNpoints());
57 if (total_events == 0) {
62 std::unique_ptr<std::vector<uint64_t>> event_index = std::make_unique<std::vector<uint64_t>>();
74 auto event_detid = std::make_unique<std::vector<uint32_t>>();
75 auto event_time_of_flight = std::make_unique<std::vector<float>>();
76 auto pulse_times_idx = std::make_unique<std::vector<size_t>>();
79 while (!eventRanges.empty()) {
83 std::vector<size_t> offsets;
84 std::vector<size_t> slabsizes;
86 size_t total_events_to_read = 0;
90 auto eventRange = eventRanges.top();
93 size_t range_size = eventRange.second - eventRange.first;
97 if (range_size > remaining_chunk) {
99 offsets.push_back(eventRange.first);
100 slabsizes.push_back(remaining_chunk);
101 total_events_to_read += remaining_chunk;
103 eventRanges.emplace(eventRange.first + remaining_chunk, eventRange.second);
106 offsets.push_back(eventRange.first);
107 slabsizes.push_back(range_size);
108 total_events_to_read += range_size;
116 if (total_events_to_read == 0) {
121 this->
loadEvents(detID_SDS, tof_SDS, offsets, slabsizes, event_detid, event_time_of_flight);
123 pulse_times_idx->resize(total_events_to_read);
126 auto event_index_it = event_index->cbegin();
127 for (
size_t i = 0; i < offsets.size(); ++i) {
128 const size_t off = offsets[i];
129 const size_t slab = slabsizes[i];
130 for (
size_t j = 0; j < slab; ++j) {
131 const uint64_t global_idx =
static_cast<uint64_t
>(off + j);
133 while (event_index_it != event_index->cend() && *event_index_it <= global_idx) {
136 size_t pulse_idx = 0;
137 if (event_index_it != event_index->cbegin()) {
138 pulse_idx =
static_cast<size_t>(std::distance(event_index->cbegin(), event_index_it) - 1);
140 (*pulse_times_idx)[pos++] = pulse_idx;
147 [&](
const tbb::blocked_range<size_t> &output_range) {
148 for (size_t output_index = output_range.begin(); output_index < output_range.end();
150 const auto calibration = calibrations.at(output_index);
152 tbb::blocked_range<size_t>(0, m_workspaceIndices.size()), [&](const tbb::blocked_range<size_t> &r) {
153 for (size_t idx = r.begin(); idx != r.end(); ++idx) {
154 int i = m_workspaceIndices[idx];
157 std::vector<size_t> indices;
158 auto splitter_it = m_splitterMap.cbegin();
159 for (size_t k = 0; k < event_detid->size(); ++k) {
162 const double correctionFactor =
163 calibration.value_scale_at_sample(static_cast<detid_t>((*event_detid)[k]));
165 const auto tof_in_nanoseconds =
166 static_cast<int64_t>(static_cast<double>((*event_time_of_flight)[k]) * correctionFactor);
167 const auto pulsetime = (*m_pulse_times)[(*pulse_times_idx)[k]];
168 const Mantid::Types::Core::DateAndTime full_time = pulsetime + tof_in_nanoseconds;
174 while (splitter_it != m_splitterMap.end() &&
175 splitter_it->first <= pulsetime - static_cast<int64_t>(PULSETIME_OFFSET)) {
182 auto full_time_it = splitter_it;
183 while (full_time_it != m_splitterMap.end() && full_time_it->first <= full_time) {
189 if (full_time_it == m_splitterMap.begin()) {
193 if (full_time_it != m_splitterMap.end() && full_time_it->second == i) {
194 indices.push_back(k);
199 auto event_id_view_for_target =
200 indices | std::views::transform([&event_detid](const auto &k) { return (*event_detid)[k]; });
201 auto event_tof_view_for_target =
202 indices | std::views::transform(
203 [&event_time_of_flight](const auto &k) { return (*event_time_of_flight)[k]; });
205 ProcessEventsTask task(&event_id_view_for_target, &event_tof_view_for_target, &calibration,
206 m_processingDatas[i].binedges[output_index]);
208 const tbb::blocked_range<size_t> range_info(0, indices.size(), m_grainsize_event);
209 tbb::parallel_reduce(range_info, task);
213 for (size_t j = 0; j < m_processingDatas[i].counts[output_index].size(); ++j) {
214 m_processingDatas[i].counts[output_index][j].fetch_add(task.y_temp[j],
215 std::memory_order_relaxed);