From 41aad93bc89eae3614da4501a7aba8d88cd4c9f4 Mon Sep 17 00:00:00 2001 From: LTLA Date: Mon, 13 Jan 2025 00:49:53 +0000 Subject: [PATCH] =?UTF-8?q?Deploying=20to=20gh-pages=20from=20@=20libscran?= =?UTF-8?q?/scran=5Faggregate@e77c1e8b1dd2fe97f587928c8d9cb910bbab19ea=20?= =?UTF-8?q?=F0=9F=9A=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- docs/aggregate__across__cells_8hpp.html | 17 +- docs/aggregate__across__cells_8hpp__incl.map | 16 +- docs/aggregate__across__cells_8hpp__incl.md5 | 2 +- docs/aggregate__across__cells_8hpp__incl.png | Bin 9027 -> 13103 bytes .../aggregate__across__cells_8hpp_source.html | 523 ++++++++-------- docs/aggregate__across__genes_8hpp.html | 25 +- docs/aggregate__across__genes_8hpp__incl.map | 24 +- docs/aggregate__across__genes_8hpp__incl.md5 | 2 +- docs/aggregate__across__genes_8hpp__incl.png | Bin 13740 -> 17570 bytes .../aggregate__across__genes_8hpp_source.html | 568 +++++++++--------- docs/clean__factor_8hpp_source.html | 2 +- docs/combine__factors_8hpp_source.html | 2 +- docs/index.html | 8 +- docs/scran__aggregate_8hpp.html | 71 +-- docs/scran__aggregate_8hpp__incl.map | 71 +-- docs/scran__aggregate_8hpp__incl.md5 | 2 +- docs/scran__aggregate_8hpp__incl.png | Bin 48767 -> 54728 bytes docs/scran__aggregate_8hpp_source.html | 2 +- 18 files changed, 653 insertions(+), 682 deletions(-) diff --git a/docs/aggregate__across__cells_8hpp.html b/docs/aggregate__across__cells_8hpp.html index c425581..5f442e2 100644 --- a/docs/aggregate__across__cells_8hpp.html +++ b/docs/aggregate__across__cells_8hpp.html @@ -95,18 +95,21 @@
#include <algorithm>
#include <vector>
#include "tatami/tatami.hpp"
+#include "tatami_stats/tatami_stats.hpp"
Include dependency graph for aggregate_across_cells.hpp:
- - - - - - - + + + + + + + + +
diff --git a/docs/aggregate__across__cells_8hpp__incl.map b/docs/aggregate__across__cells_8hpp__incl.map index 7a883f5..3b1ae8d 100644 --- a/docs/aggregate__across__cells_8hpp__incl.map +++ b/docs/aggregate__across__cells_8hpp__incl.map @@ -1,9 +1,11 @@ - - - - - - - + + + + + + + + + diff --git a/docs/aggregate__across__cells_8hpp__incl.md5 b/docs/aggregate__across__cells_8hpp__incl.md5 index 556a471..896357c 100644 --- a/docs/aggregate__across__cells_8hpp__incl.md5 +++ b/docs/aggregate__across__cells_8hpp__incl.md5 @@ -1 +1 @@ -b72cfb3808a6169684e1c0c68fde63d8 \ No newline at end of file +a5850818d6e39fc80cd613493ca5e12c \ No newline at end of file diff --git a/docs/aggregate__across__cells_8hpp__incl.png b/docs/aggregate__across__cells_8hpp__incl.png index 96630e199a4d7e312d69d7bb4ca07f54c656cd14..8fd1ae31e091cf1022d45efecdf382827aa7b298 100644 GIT binary patch literal 13103 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 D-TMGt diff --git a/docs/aggregate__across__cells_8hpp_source.html b/docs/aggregate__across__cells_8hpp_source.html index 6e748ac..74160e6 100644 --- a/docs/aggregate__across__cells_8hpp_source.html +++ b/docs/aggregate__across__cells_8hpp_source.html @@ -97,295 +97,266 @@
5#include <vector>
6
7#include "tatami/tatami.hpp"
-
8
-
-
14namespace scran_aggregate {
-
15
-
- -
24 bool compute_sums = true;
-
25
-
30 bool compute_detected = true;
-
31
-
36 int num_threads = 1;
-
37};
+
8#include "tatami_stats/tatami_stats.hpp"
+
9
+
+
15namespace scran_aggregate {
+
16
+
+ +
25 bool compute_sums = true;
+
26
+
31 bool compute_detected = true;
+
32
+
37 int num_threads = 1;
+
38};
-
38
-
44template <typename Sum_, typename Detected_>
-
- -
53 std::vector<Sum_*> sums;
-
54
-
62 std::vector<Detected_*> detected;
-
63
-
64};
+
39
+
45template <typename Sum_, typename Detected_>
+
+ +
54 std::vector<Sum_*> sums;
+
55
+
63 std::vector<Detected_*> detected;
+
64
+
65};
-
65
-
71template <typename Sum_, typename Detected_>
-
- -
80 std::vector<std::vector<Sum_> > sums;
-
81
-
89 std::vector<std::vector<Detected_> > detected;
-
90};
+
66
+
72template <typename Sum_, typename Detected_>
+
+ +
81 std::vector<std::vector<Sum_> > sums;
+
82
+
90 std::vector<std::vector<Detected_> > detected;
+
91};
-
91
-
95namespace internal {
-
96
-
97template<bool sparse_, typename Data_, typename Index_, typename Factor_, typename Sum_, typename Detected_>
-
98void compute_aggregate_by_row(
- -
100 const Factor_* factor,
- -
102 const AggregateAcrossCellsOptions& options)
-
103{
-
104 tatami::Options opt;
-
105 opt.sparse_ordered_index = false;
-
106
-
107 tatami::parallelize([&](size_t, Index_ s, Index_ l) {
-
108 auto ext = tatami::consecutive_extractor<sparse_>(&p, true, s, l, opt);
-
109 size_t nsums = buffers.sums.size();
-
110 std::vector<Sum_> tmp_sums(nsums);
-
111 size_t ndetected = buffers.detected.size();
-
112 std::vector<Detected_> tmp_detected(ndetected);
-
113
-
114 auto NC = p.ncol();
-
115 std::vector<Data_> vbuffer(NC);
-
116 typename std::conditional<sparse_, std::vector<Index_>, Index_>::type ibuffer(NC);
-
117
-
118 for (Index_ x = s, end = s + l; x < end; ++x) {
-
119 auto row = [&]() {
-
120 if constexpr(sparse_) {
-
121 return ext->fetch(vbuffer.data(), ibuffer.data());
-
122 } else {
-
123 return ext->fetch(vbuffer.data());
-
124 }
-
125 }();
-
126
-
127 if (nsums) {
-
128 std::fill(tmp_sums.begin(), tmp_sums.end(), 0);
-
129
-
130 if constexpr(sparse_) {
-
131 for (Index_ j = 0; j < row.number; ++j) {
-
132 tmp_sums[factor[row.index[j]]] += row.value[j];
-
133 }
-
134 } else {
-
135 for (Index_ j = 0; j < NC; ++j) {
-
136 tmp_sums[factor[j]] += row[j];
-
137 }
-
138 }
-
139
-
140 // Computing before transferring for more cache-friendliness.
-
141 for (size_t l = 0; l < nsums; ++l) {
-
142 buffers.sums[l][x] = tmp_sums[l];
-
143 }
-
144 }
-
145
-
146 if (ndetected) {
-
147 std::fill(tmp_detected.begin(), tmp_detected.end(), 0);
-
148
-
149 if constexpr(sparse_) {
-
150 for (Index_ j = 0; j < row.number; ++j) {
-
151 tmp_detected[factor[row.index[j]]] += (row.value[j] > 0);
-
152 }
-
153 } else {
-
154 for (Index_ j = 0; j < NC; ++j) {
-
155 tmp_detected[factor[j]] += (row[j] > 0);
-
156 }
-
157 }
-
158
-
159 for (size_t l = 0; l < ndetected; ++l) {
-
160 buffers.detected[l][x] = tmp_detected[l];
-
161 }
-
162 }
-
163 }
-
164 }, p.nrow(), options.num_threads);
-
165}
-
166
-
167template<bool sparse_, typename Data_, typename Index_, typename Factor_, typename Sum_, typename Detected_>
-
168void compute_aggregate_by_column(
- -
170 const Factor_* factor,
-
171 const AggregateAcrossCellsBuffers<Sum_, Detected_>& buffers,
-
172 const AggregateAcrossCellsOptions& options)
-
173{
-
174 tatami::Options opt;
-
175 opt.sparse_ordered_index = false;
-
176
-
177 tatami::parallelize([&](size_t t, Index_ start, Index_ length) {
-
178 auto NC = p.ncol();
-
179 auto ext = tatami::consecutive_extractor<sparse_>(&p, false, static_cast<Index_>(0), NC, start, length, opt);
-
180 std::vector<Data_> vbuffer(length);
-
181 typename std::conditional<sparse_, std::vector<Index_>, Index_>::type ibuffer(length);
-
182
-
183 // Creating local buffers to protect against false sharing in all but
-
184 // the first thread. The first thread has the honor of writing directly
-
185 // to the output buffers, to avoid extra allocations in the serial case
-
186 // where no false sharing can occur.
-
187 std::vector<std::vector<Sum_> > local_sums;
-
188 std::vector<std::vector<Detected_> > local_detected;
-
189 size_t num_sums = buffers.sums.size();
-
190 size_t num_detected = buffers.detected.size();
-
191 if (t != 0) {
-
192 local_sums.reserve(num_sums);
-
193 for (size_t s = 0; s < num_sums; ++s) {
-
194 local_sums.emplace_back(length);
-
195 }
-
196 local_detected.reserve(num_detected);
-
197 for (size_t d = 0; d < num_detected; ++d) {
-
198 local_detected.emplace_back(length);
-
199 }
-
200 } else {
-
201 // Need to zero it in the first thread for consistency with the other threads.
-
202 for (size_t s = 0; s < num_sums; ++s) {
-
203 std::fill_n(buffers.sums[s] + start, length, static_cast<Sum_>(0));
-
204 }
-
205 for (size_t d = 0; d < num_sums; ++d) {
-
206 std::fill_n(buffers.detected[d] + start, length, static_cast<Detected_>(0));
-
207 }
-
208 }
-
209
-
210 for (Index_ x = 0; x < NC; ++x) {
-
211 auto current = factor[x];
-
212
-
213 if constexpr(sparse_) {
-
214 auto col = ext->fetch(vbuffer.data(), ibuffer.data());
-
215 if (num_sums) {
-
216 auto cursum = (t != 0 ? local_sums[current].data() : buffers.sums[current] + start);
-
217 for (Index_ i = 0; i < col.number; ++i) {
-
218 cursum[col.index[i] - start] += col.value[i];
-
219 }
-
220 }
-
221
-
222 if (num_detected) {
-
223 auto curdetected = (t != 0 ? local_detected[current].data() : buffers.detected[current] + start);
-
224 for (Index_ i = 0; i < col.number; ++i) {
-
225 curdetected[col.index[i] - start] += (col.value[i] > 0);
-
226 }
-
227 }
-
228
-
229 } else {
-
230 auto col = ext->fetch(vbuffer.data());
-
231 if (num_sums) {
-
232 auto cursum = (t != 0 ? local_sums[current].data() : buffers.sums[current] + start);
-
233 for (Index_ i = 0; i < length; ++i) {
-
234 cursum[i] += col[i];
-
235 }
-
236 }
-
237
-
238 if (num_detected) {
-
239 auto curdetected = (t != 0 ? local_detected[current].data() : buffers.detected[current] + start);
-
240 for (Index_ i = 0; i < length; ++i) {
-
241 curdetected[i] += (col[i] > 0);
-
242 }
-
243 }
-
244 }
-
245 }
-
246
-
247 if (t != 0) {
-
248 for (size_t s = 0; s < num_sums; ++s) {
-
249 const auto& current = local_sums[s];
-
250 std::copy(current.begin(), current.end(), buffers.sums[s] + start);
-
251 }
-
252 for (size_t d = 0; d < num_detected; ++d) {
-
253 const auto& current = local_detected[d];
-
254 std::copy(current.begin(), current.end(), buffers.detected[d] + start);
-
255 }
-
256 }
-
257 }, p.nrow(), options.num_threads);
-
258}
-
259
-
260}
-
284template<typename Data_, typename Index_, typename Factor_, typename Sum_, typename Detected_>
-
- - -
287 const Factor_* factor,
- -
289 const AggregateAcrossCellsOptions& options)
-
290{
-
291 if (input.prefer_rows()) {
-
292 if (input.sparse()) {
-
293 internal::compute_aggregate_by_row<true>(input, factor, buffers, options);
-
294 } else {
-
295 internal::compute_aggregate_by_row<false>(input, factor, buffers, options);
-
296 }
-
297 } else {
-
298 if (input.sparse()) {
-
299 internal::compute_aggregate_by_column<true>(input, factor, buffers, options);
-
300 } else {
-
301 internal::compute_aggregate_by_column<false>(input, factor, buffers, options);
-
302 }
-
303 }
-
304}
+
92
+
96namespace internal {
+
97
+
98template<bool sparse_, typename Data_, typename Index_, typename Factor_, typename Sum_, typename Detected_>
+
99void compute_aggregate_by_row(
+ +
101 const Factor_* factor,
+ +
103 const AggregateAcrossCellsOptions& options)
+
104{
+
105 tatami::Options opt;
+
106 opt.sparse_ordered_index = false;
+
107
+
108 tatami::parallelize([&](size_t, Index_ s, Index_ l) {
+
109 auto ext = tatami::consecutive_extractor<sparse_>(&p, true, s, l, opt);
+
110 size_t nsums = buffers.sums.size();
+
111 std::vector<Sum_> tmp_sums(nsums);
+
112 size_t ndetected = buffers.detected.size();
+
113 std::vector<Detected_> tmp_detected(ndetected);
+
114
+
115 auto NC = p.ncol();
+
116 std::vector<Data_> vbuffer(NC);
+
117 typename std::conditional<sparse_, std::vector<Index_>, Index_>::type ibuffer(NC);
+
118
+
119 for (Index_ x = s, end = s + l; x < end; ++x) {
+
120 auto row = [&]() {
+
121 if constexpr(sparse_) {
+
122 return ext->fetch(vbuffer.data(), ibuffer.data());
+
123 } else {
+
124 return ext->fetch(vbuffer.data());
+
125 }
+
126 }();
+
127
+
128 if (nsums) {
+
129 std::fill(tmp_sums.begin(), tmp_sums.end(), 0);
+
130
+
131 if constexpr(sparse_) {
+
132 for (Index_ j = 0; j < row.number; ++j) {
+
133 tmp_sums[factor[row.index[j]]] += row.value[j];
+
134 }
+
135 } else {
+
136 for (Index_ j = 0; j < NC; ++j) {
+
137 tmp_sums[factor[j]] += row[j];
+
138 }
+
139 }
+
140
+
141 // Computing before transferring for more cache-friendliness.
+
142 for (size_t l = 0; l < nsums; ++l) {
+
143 buffers.sums[l][x] = tmp_sums[l];
+
144 }
+
145 }
+
146
+
147 if (ndetected) {
+
148 std::fill(tmp_detected.begin(), tmp_detected.end(), 0);
+
149
+
150 if constexpr(sparse_) {
+
151 for (Index_ j = 0; j < row.number; ++j) {
+
152 tmp_detected[factor[row.index[j]]] += (row.value[j] > 0);
+
153 }
+
154 } else {
+
155 for (Index_ j = 0; j < NC; ++j) {
+
156 tmp_detected[factor[j]] += (row[j] > 0);
+
157 }
+
158 }
+
159
+
160 for (size_t l = 0; l < ndetected; ++l) {
+
161 buffers.detected[l][x] = tmp_detected[l];
+
162 }
+
163 }
+
164 }
+
165 }, p.nrow(), options.num_threads);
+
166}
+
167
+
168template<bool sparse_, typename Data_, typename Index_, typename Factor_, typename Sum_, typename Detected_>
+
169void compute_aggregate_by_column(
+ +
171 const Factor_* factor,
+
172 const AggregateAcrossCellsBuffers<Sum_, Detected_>& buffers,
+
173 const AggregateAcrossCellsOptions& options)
+
174{
+
175 tatami::Options opt;
+
176 opt.sparse_ordered_index = false;
+
177
+
178 tatami::parallelize([&](size_t t, Index_ start, Index_ length) {
+
179 auto NC = p.ncol();
+
180 auto ext = tatami::consecutive_extractor<sparse_>(&p, false, static_cast<Index_>(0), NC, start, length, opt);
+
181 std::vector<Data_> vbuffer(length);
+
182 typename std::conditional<sparse_, std::vector<Index_>, Index_>::type ibuffer(length);
+
183
+
184 size_t num_sums = buffers.sums.size();
+
185 auto get_sum = [&](Index_ i) -> Sum_* { return buffers.sums[i]; };
+
186 tatami_stats::LocalOutputBuffers<Sum_, decltype(get_sum)> local_sums(t, num_sums, start, length, std::move(get_sum));
+
187 auto get_detected = [&](Index_ i) -> Detected_* { return buffers.detected[i]; };
+
188 size_t num_detected = buffers.detected.size();
+
189 tatami_stats::LocalOutputBuffers<Detected_, decltype(get_detected)> local_detected(t, num_detected, start, length, std::move(get_detected));
+
190
+
191 for (Index_ x = 0; x < NC; ++x) {
+
192 auto current = factor[x];
+
193
+
194 if constexpr(sparse_) {
+
195 auto col = ext->fetch(vbuffer.data(), ibuffer.data());
+
196 if (num_sums) {
+
197 auto cursum = local_sums.data(current);
+
198 for (Index_ i = 0; i < col.number; ++i) {
+
199 cursum[col.index[i] - start] += col.value[i];
+
200 }
+
201 }
+
202 if (num_detected) {
+
203 auto curdetected = local_detected.data(current);
+
204 for (Index_ i = 0; i < col.number; ++i) {
+
205 curdetected[col.index[i] - start] += (col.value[i] > 0);
+
206 }
+
207 }
+
208
+
209 } else {
+
210 auto col = ext->fetch(vbuffer.data());
+
211 if (num_sums) {
+
212 auto cursum = local_sums.data(current);
+
213 for (Index_ i = 0; i < length; ++i) {
+
214 cursum[i] += col[i];
+
215 }
+
216 }
+
217 if (num_detected) {
+
218 auto curdetected = local_detected.data(current);
+
219 for (Index_ i = 0; i < length; ++i) {
+
220 curdetected[i] += (col[i] > 0);
+
221 }
+
222 }
+
223 }
+
224 }
+
225
+
226 local_sums.transfer();
+
227 local_detected.transfer();
+
228 }, p.nrow(), options.num_threads);
+
229}
+
230
+
231}
+
255template<typename Data_, typename Index_, typename Factor_, typename Sum_, typename Detected_>
+
+ + +
258 const Factor_* factor,
+ +
260 const AggregateAcrossCellsOptions& options)
+
261{
+
262 if (input.prefer_rows()) {
+
263 if (input.sparse()) {
+
264 internal::compute_aggregate_by_row<true>(input, factor, buffers, options);
+
265 } else {
+
266 internal::compute_aggregate_by_row<false>(input, factor, buffers, options);
+
267 }
+
268 } else {
+
269 if (input.sparse()) {
+
270 internal::compute_aggregate_by_column<true>(input, factor, buffers, options);
+
271 } else {
+
272 internal::compute_aggregate_by_column<false>(input, factor, buffers, options);
+
273 }
+
274 }
+
275}
-
305
-
323template<typename Sum_ = double, typename Detected_ = int, typename Data_, typename Index_, typename Factor_>
-
- - -
326 const Factor_* factor,
-
327 const AggregateAcrossCellsOptions& options)
-
328{
-
329 size_t NC = input.ncol();
-
330 size_t nlevels = (NC ? *std::max_element(factor, factor + NC) + 1 : 0);
-
331 size_t ngenes = input.nrow();
-
332
- - -
335
-
336 if (options.compute_sums) {
-
337 output.sums.resize(nlevels, std::vector<Sum_>(ngenes
-
338#ifdef SCRAN_AGGREGATE_TEST_INIT
-
339 , SCRAN_AGGREGATE_TEST_INIT
-
340#endif
-
341 ));
-
342 buffers.sums.resize(nlevels);
-
343 for (size_t l = 0; l < nlevels; ++l) {
-
344 buffers.sums[l] = output.sums[l].data();
-
345 }
-
346 }
-
347
-
348 if (options.compute_detected) {
-
349 output.detected.resize(nlevels, std::vector<Detected_>(ngenes
-
350#ifdef SCRAN_AGGREGATE_TEST_INIT
-
351 , SCRAN_AGGREGATE_TEST_INIT
-
352#endif
-
353 ));
-
354 buffers.detected.resize(nlevels);
-
355 for (size_t l = 0; l < nlevels; ++l) {
-
356 buffers.detected[l] = output.detected[l].data();
-
357 }
-
358 }
-
359
-
360 aggregate_across_cells(input, factor, buffers, options);
-
361 return output;
-
362}
+
276
+
294template<typename Sum_ = double, typename Detected_ = int, typename Data_, typename Index_, typename Factor_>
+
+ + +
297 const Factor_* factor,
+
298 const AggregateAcrossCellsOptions& options)
+
299{
+
300 size_t NC = input.ncol();
+
301 size_t nlevels = (NC ? *std::max_element(factor, factor + NC) + 1 : 0);
+
302 size_t ngenes = input.nrow();
+
303
+ + +
306
+
307 if (options.compute_sums) {
+
308 output.sums.resize(nlevels, std::vector<Sum_>(ngenes
+
309#ifdef SCRAN_AGGREGATE_TEST_INIT
+
310 , SCRAN_AGGREGATE_TEST_INIT
+
311#endif
+
312 ));
+
313 buffers.sums.resize(nlevels);
+
314 for (size_t l = 0; l < nlevels; ++l) {
+
315 buffers.sums[l] = output.sums[l].data();
+
316 }
+
317 }
+
318
+
319 if (options.compute_detected) {
+
320 output.detected.resize(nlevels, std::vector<Detected_>(ngenes
+
321#ifdef SCRAN_AGGREGATE_TEST_INIT
+
322 , SCRAN_AGGREGATE_TEST_INIT
+
323#endif
+
324 ));
+
325 buffers.detected.resize(nlevels);
+
326 for (size_t l = 0; l < nlevels; ++l) {
+
327 buffers.detected[l] = output.detected[l].data();
+
328 }
+
329 }
+
330
+
331 aggregate_across_cells(input, factor, buffers, options);
+
332 return output;
+
333}
-
363
-
364}
+
334
+
335}
-
365
-
366#endif
+
336
+
337#endif
virtual Index_ ncol() const=0
virtual Index_ nrow() const=0
virtual bool prefer_rows() const=0
virtual std::unique_ptr< MyopicSparseExtractor< Value_, Index_ > > sparse(bool row, const Options &opt) const=0
-
Aggregate single-cell expression values.
Definition aggregate_across_cells.hpp:14
-
void aggregate_across_cells(const tatami::Matrix< Data_, Index_ > &input, const Factor_ *factor, const AggregateAcrossCellsBuffers< Sum_, Detected_ > &buffers, const AggregateAcrossCellsOptions &options)
Definition aggregate_across_cells.hpp:285
+
Aggregate single-cell expression values.
Definition aggregate_across_cells.hpp:15
+
void aggregate_across_cells(const tatami::Matrix< Data_, Index_ > &input, const Factor_ *factor, const AggregateAcrossCellsBuffers< Sum_, Detected_ > &buffers, const AggregateAcrossCellsOptions &options)
Definition aggregate_across_cells.hpp:256
void parallelize(Function_ fun, Index_ tasks, int threads)
auto consecutive_extractor(const Matrix< Value_, Index_ > *mat, bool row, Index_ iter_start, Index_ iter_length, Args_ &&... args)
-
Buffers for aggregate_across_cells().
Definition aggregate_across_cells.hpp:45
-
std::vector< Detected_ * > detected
Definition aggregate_across_cells.hpp:62
-
std::vector< Sum_ * > sums
Definition aggregate_across_cells.hpp:53
-
Options for aggregate_across_cells().
Definition aggregate_across_cells.hpp:19
-
int num_threads
Definition aggregate_across_cells.hpp:36
-
bool compute_detected
Definition aggregate_across_cells.hpp:30
-
bool compute_sums
Definition aggregate_across_cells.hpp:24
-
Results of aggregate_across_cells().
Definition aggregate_across_cells.hpp:72
-
std::vector< std::vector< Detected_ > > detected
Definition aggregate_across_cells.hpp:89
-
std::vector< std::vector< Sum_ > > sums
Definition aggregate_across_cells.hpp:80
+
Buffers for aggregate_across_cells().
Definition aggregate_across_cells.hpp:46
+
std::vector< Detected_ * > detected
Definition aggregate_across_cells.hpp:63
+
std::vector< Sum_ * > sums
Definition aggregate_across_cells.hpp:54
+
Options for aggregate_across_cells().
Definition aggregate_across_cells.hpp:20
+
int num_threads
Definition aggregate_across_cells.hpp:37
+
bool compute_detected
Definition aggregate_across_cells.hpp:31
+
bool compute_sums
Definition aggregate_across_cells.hpp:25
+
Results of aggregate_across_cells().
Definition aggregate_across_cells.hpp:73
+
std::vector< std::vector< Detected_ > > detected
Definition aggregate_across_cells.hpp:90
+
std::vector< std::vector< Sum_ > > sums
Definition aggregate_across_cells.hpp:81
bool sparse_ordered_index
diff --git a/docs/aggregate__across__genes_8hpp.html b/docs/aggregate__across__genes_8hpp.html index 857dfeb..93c879e 100644 --- a/docs/aggregate__across__genes_8hpp.html +++ b/docs/aggregate__across__genes_8hpp.html @@ -97,22 +97,25 @@ #include <unordered_set>
#include <stdexcept>
#include "tatami/tatami.hpp"
+#include "tatami_stats/tatami_stats.hpp"
Include dependency graph for aggregate_across_genes.hpp:
- - - - - - - - - - - + + + + + + + + + + + + +
diff --git a/docs/aggregate__across__genes_8hpp__incl.map b/docs/aggregate__across__genes_8hpp__incl.map index a652c8c..23bc26f 100644 --- a/docs/aggregate__across__genes_8hpp__incl.map +++ b/docs/aggregate__across__genes_8hpp__incl.map @@ -1,13 +1,15 @@ - - - - - - - - - - - + + + + + + + + + + + + + diff --git a/docs/aggregate__across__genes_8hpp__incl.md5 b/docs/aggregate__across__genes_8hpp__incl.md5 index ec7799b..54f2f86 100644 --- a/docs/aggregate__across__genes_8hpp__incl.md5 +++ b/docs/aggregate__across__genes_8hpp__incl.md5 @@ -1 +1 @@ -6fa151930ef3853992bf2df66624d6b1 \ No newline at end of file +f55e61a274620c8ce209809a4a6ab120 \ No newline at end of file diff --git a/docs/aggregate__across__genes_8hpp__incl.png b/docs/aggregate__across__genes_8hpp__incl.png index 153f361abf815dd21570a4f4f7be69b3a05c9362..d58d681223a2cd75fc43314dbf97b58783ba2a78 100644 GIT binary patch literal 17570 zcmZv^1z1*V&^8KU(I_AxAxeixgPv*ww(=bm});j@g?TWkzc3=|X;Y*CTdawsU*YT^5!+c)8>yN^x- z{O_i&_}kYg|B!!D>$4+JP#&O&zJ96ToVYpV;x3`|uW7F@u7mOJ-P$&(p@uvf)0m%f z;{lbG4>P5Sx()<1a-J6ye!DMR^}sj}bBYkXB$_cT+BDCUj{3tFyfMSxozV7+QYl*M zIEj6aMomrDjvBjOr)}obX}7*h3Ou3PRKEZJUkK<7c2In+2|}Nr87q~IssEa`xh+d@ zk43e7V4CeV)oW4fQYRE4UW~G_3(BlPYqwuiukVEEE8UiTEK2~=@>s2 zmF3t{R}7!cyl;IAo{;}ty<&LZe;-RgBh+XLq4SZH`8* zBioyIb(Twfm{h(eUdTJiK6dCoWMssM=+OUjq-yq9LG)O?ozThLoH>Ep;^Fh> z$=@9|*x{Dy>gpI|j~YksJyyTn^urI6gx`^w%XF~#Y1`hyFO$(?of_9(uv}>bN39S+ zgqG*2pH<^!v|&&D?@|NthVyNH$F1=j`qba88cu1Wn3TR+OjK@8*C!M;oMCvMoH#pf zjy8Y9zQ22TxKz}5^^lo4=q5HPvNow?fsXy9E|v)}Z#0KdZ-2&H-11>&@u(@L$aT-(s9boUh!^12v3NIg@Y@??~ zVp0;SzrTN~+wnFQDd%l(uuLgzPnRA(KEBK0kdlq9?fha##KnfzzjWcidnnb_)y1Ym zj9rzMmX-qh?T_fQj7N*9{$1{PiAqS6Czf;v*4DZ;cob?iQV0qP-o&NAdXe!a*m=8V z1;f0HY0798wYERff|B4xCew9%o}QjB+Eg06y-~U<9o7eR zHb+aMQ#OVR0wd(xe*GC4iAmyjx_j?l8$=MSw3|DmsEAdJ0fkW^M_b-}_$(+Sg!ajk z{{6Dh&`=ti%He2^?bTJ|@Q4VPl_V$Tt=!z)pFe*pZ)K;hBt%uPB_<|TFNE-S4%tN` z5oH^JEK084)gjqsnWRv&zBBC6TW}vVHa0eai`|y$nwqf0MDsCj7M9?aPq=@;d%VpL zSe5dXoBc3}h@ZRjI&2It{rrsY>*uF39{ffxO|NV?ySA2JR8%zDqGC8&xu9YxXku(E z4!m0J>mB|5zkl`5kG4*a(8@t<%ArOY2C8wo5K=V#rE>S2Sg(c#36-MXe6z z;uok@EqBLppp+Z`{*dBz6&D#vfWmDx-5sOlX~Op^;hnub=hk>d#!H`@FWMv(Z}fDq z_*Xnvt2B>esRYMw-S;xH;H!Z5zWRhSx3wi1Ov+X5dHJ-=sE?M0rqxuiQa}r!ZI<{~ z2ziFhLfikYq!(GqO&qfJ^PR>%!G9M%fE!#~QKAvFsQpD+f>KFOTZ2eAteu=z+Jf)< z`uZ-8N$*V8pI#jFjn%vH?CtIS-5iVX^}X(SvG;azYRZa%+sxzU&6~D=S7i;mV_(9v zg(fp ztSIp5q`IB3%Ep31L!~QyK9yc2*4Nitt<^v9#WT>@{v#sfFCZDuX%bacb-ath;>yfz717gKn~(l8i0?L%DYr{Yk;SU?z%h; zmMzh3wLMOR%(EyNu0hqAs^xVV1^HxgV!A+$2XH&eNUcb-p4WaA?@zXLwr*mIkCgcv-;`dXS%Z)$000NCH{sf4q`4K$LNjkm$1!mnRnN1~*#c3bz)S4pyGt^~NaxZfSO z#3E=VQL63N?uLbhsaIR0Qc_ah#3FtHdyQdU)@II)PeRi1JL4^~--jC`EA3&A1pfBF zGA=khT}e6JC~CB}v&#TC9_uE8% zrx3^`a@kVkz$<=sM9`rsH@Nf3%F5brj^1HqWu10eA)lY0_YUehgcOOEDwie3tXUWP z%9lKmY{@!TiPPfwQx7vD1#GVPA4^b~atoQ->eMoVIg6Zgi3K06zZ7Q(}cM<#XPB z0O-`#)rHy4dq7G-AvN{gp~iXdVW`0VZKr7$I%KP1tAI>cPF9CmB{YBeS8~`INHkVu zl|sYau1v+u%^eNfRss(QDPI_N3*`whmN{HpyZs%rUHNMjyo!>@XZH~}jf#glEChov zyRlIazA61niI1;ma-Y}wfydcj)Kq}gy8TWjtoz*ErfQynn&8{?uE3;ZKSBZ>%((-9 zUcY@C0l)#KL*aGWCPMFfO0Hr-Jk9SO^NBha4hjkixK$9Y-~}Ey zBPoxiM3vF<*V49~-Nqw4|j8Z%dO~l2-fK0XS+kqKa{uRlj zT^lLXC_}a-&Vf*Xh=>TRpmSOS*d6^3Ub*k&;)`7Z(@1fB#a$egTVrA5KI=ny2bae)Wni&u=iNItH(KLj zV?}gz(i|TV|Iq&5i?%g{MQ1`7JG;4Y*ey!{`*`7pL1;W)&R{m2 zp9X1BBKFDq;^HTsXKQp2uf{{)q6{9JDgssoQ3@u5Z`{3e=cTUh!-j?iEDC{9xw*Ne z7_F~>v_IS01}ZJo;<+sX1q4>^`$xXPw36}Vof8vo&dYVf1D)pFcH5JD@X5KV6^w>uaR9xhL*M+$$~e~6 z))EE1k}(JwWwOKwyB0zyo{0gqvvzc>ym;JbL6u=YGL)wT`Lx4fZAMkilkHb)E8-iE z)vI3s`yH#cd9>1(Vsvq`H>PW2W7Fa2$Z0eg^H}4DKD#WiuDsB)dn=Hgyn|dShtE>j z4FZ;$<{?`QetU;WmmOqxdw6_v4X9@#ug!=4ewouNBB4mkqkqeULIeyx&E7>tMN38* zzhk##m2NhCf&n23(tE*vcP46&*&8^Z9Fk~X&Ejl_nrt+^^#l%9?+wT5&6T%MZ&rBckVR~H{WHTfc{(q}C*ad%f zaZ4HebUfe$ypEf(^)2*582v{$KT!F$J-gHw;ccCmP#6}6HEWN?g@+4?iHYrD&1!b2 zjBLyJj2D>cSUbw8&5WxEprJm;7I4VBrE0w(7Cv5oqHTkf#vfwUdWy!zcve+CzbY89 zpELh$BG^)RaKI;%I`iI&a@^l%(hfs6>3sHfrM=c;U+vMb8G3ft8=cH8uIJB7Yb^dq zDM`HCN@vfG+aieom!Y-gDa3Q+^eia+iiL$nA=7`pT*Q-pV*0sJRdaAbQa#Uuja}S~ z0u_g;rz{X{Xgr<5NY0nSd^mqN{=DVdkdyF~m*N8VMrRv==PhnlbQ!%syL^e}4ST$R z6>o0(VH1urxaugJm_Hl+j%(xx6iyHC@fQz^CC#`=g3Z4#5aIO3XHlOL3Pq|R!283J zw)*{xFW0=9GO6w=8#pfgGN>PlN~hr9RX<1Rqi-cBsL3G!^3oap?oniJ&M(p`6(vWp zCA|3HK(xU}uog`*_L^SPA5XW8Wa@I#DC5bAW6ShW1k)llmU$)o2eGkf&rE_T`(qM1 ziauzNK8$*3yNBXgrsOVkTL%|ez_kw}tFFW(A8Bt3D?LzYq17g2a3|tcpt<*}nkvuX zMg&L1`!#QL=dQ(0w=UPb#d%`f2fRXF0bg1BZAHDmtE(?8lJcl~UHi+lW<&L8O?WT= z!^@@}(&^ld&XqD(rdp{l71WI+9nOMH_x*)SBn`;4EtEHlq((X30D4*?3y`3Fz5bCg ziHZk*(z1zgmX0$|9y|YXP)mcgu;kT|vC#odn^{lb3mWaT-|d_ISL>!W!RSZ)Ef_~} zy6g+?_`IRIwI4+A^VQai zdPn&c;e*AH5B8!Qb!V%W%0ym_hWV92YgYKqLv@|;M)bBYiB$$v>28$k~hiVx+M7f zrytE)*iQXb=7)ApBW{lYX^m2+e4*Pm{Ll`W=Qa?vro0w^&8XZkiG5d|oM<>|Fl!Ti z?t2RAvaxaC{QZp2Bxz{xJ`ahOjr{dfw;8p0`brA_kpuRCvjo#u)HSg(8K&h4{=z!n z{9(d@q_wZ?UjDIB7(M zF8gdcq0UWwD;A2J-f{lQ3xNg|B?+mtz)oK4)m!Dax|=*7$i2!Oi`vT43HXR7r2Gh) zINY~YbAywU?d#)aZ=zOs3%(yxJ&1VLDdqQiwN_%6J${bfF-}rK>#2+d%Nnm(%U{1l zG5P(Zp@js8)<}X6@3Xzvo0L=!RFzZDCVJBdSGDeZca4urCOu>DqwFUWxrJlRaVjaH ztyUsEbVtZv2*|j9G5ATQ;o>K+c1_>!Fxqvy+o7V{YHwSkM*bjQbU#>^i>oRqy z)>JYU7|EpBOBuEQw-HUBhyT!z-MiKVf}xw}*k? zK)mZ3VU@V)1qPK^I6R+3SJ><{ZnXhzb?0YRqGS1zqYySGw~@{Yzef^U?Hys^2Z;zY z#KyYXy$@h&63`>X6#A4y?eNH{@@cAj16ZH$D-msy>q%v$ z!DEmaz|MwngBRPF*-K`GnKbD?5H*=*Ex=Tme4M+-^dAfaukrIe=cpvarVfsSfKcLddyw%`BRih_$H4FQMLDGpm zdLFUJ?F49)l0{csA2DA($U=LUSg+SDZITydhWR$J;Y-9Lx(z;q$1-UI(q@uevrG~1 zm7=j_{*Cfi&eI}W?nl*8XiXn_nOQHNNG$Z`13yYXDK|=9V$g+*DkI?{-P?jm-Yn;y z=?YtmrJO%Rwzhv^aRw@>^De1jA1g>T)k#x5%bd(a zV5j7*>Brdc=6BJ({?Sp$dtoh{Wt`=Iirci8D_YTpijG1GGDU;6s9r0EZwAOQKn5}< z?*2ztZHOJ#^o@XHrieJ_?j~8fr0rnm;q_^0?t||cKXDE8z{&;;E`7pggmuZy#)c>w zESL%>c|%7yJrw4-duC7YD8{vtDgpic=iwRYxooMcue>|%;Hy6{DwzDPTGl<=jhR(2 z7{}7t34Yf(4t}SvlB)ZpSgS?-tyb#1BeJGWN?;HgQ;99EjUR4t{k=m@>CE$wvwp17SlLyE@!8g@)JPtOXcF>Izun#F|Oy z$*QRS?*mYXItqUVM4YN;{Jpa*go}$(h{2sOC;urS{Y%SF?C){h2Y2J=nu_SZvhFEO zz-_k}^N`!({vol&(9GB{p}Wf9#DBjbcJRLJ^YL@C{P`_%HIql+JJ#;7U%DKYWsV$Q z2mTp;aHE{vrgyNmV0$h!B5Rne6req8^%n3VZ{NPHOh6J)2=U$=XCbDqC{n5=1g(k1 zsO#XZOa*NPzqx{Mx{83o$v#1diU44|k!E#eBF4nJ!I(bwSvSgdUi@v{OQ!!agWXeU zH2L?KAqq?*_m*_P50)5e`nr56%d>3_uI*yU+)zfZtD}BFUSXx5l`?ojnEn?!l#`XI zQRAy?qDolT8G2e?aA~vd=H5~Kcr)j~5vN2%KR1dWO$2SaP}^|&!+XY70RG&41mX61 zA&@)FDmEO@a2Zc1NsO2qITKv;)?OTD*X!94xD1^Pk=$xkBYe%+6C#Ydj_dY|;k64K zB~;Ut8Je`L)vh^mG<)FXpkCy1=5_bF&*u!?+Lya$x-|YxAZ3oZ4>9ssM$#YF{o)Ts z?`t{phXRyh&hj*lLVCgwbBNu7?Mssg>L>4hqG-_FQqbCSooA{&zyNJf@F=86Bq|MH zo<0=Wu)YpYO?D-NR~-1&wRNlj#hGnIct?oq_h(v937LH;*X8W@Pe3nhZi-2}S}(3& zV8X%w;UIX!>Y4>vJpflHg1`DtUrpOG%almB)O~N^D0~;ESnj9TO<|T zT8zoFsry^;i;Ah~J;In$MWzu&+cyXQI_z(5d>C1GBtGGJf^j0>qUNA+>aJ)NWw|p- zmc+v4iH|>8V(R-{XXJ&S^%G!1fqP~Sb{V?9DtoCPYP~sB_s9(u{caRzFwaP;E1E5h z3w>o>r0wu({_x0NoU;!F7tQFs3p%>5*h58oWJ$uW!l!H>I|mnj3ez$EAY-o-V9enz zPjOeh{Ty6q4ukW$4$qRFYKQL)%}tHiPdf5NIgOu7IO!#;yRy0>@u&8v z!;;UQquEV_fr5HL;${BFq9|R1q$G1zT&+kx)1@}X)(wMPu+Jiv;T4!??t)23Nt)-N zT2bN#mTF12=)oHmhG)v82wa#W_qsz?=n<(~JsfoH!kek7%D6#7L|@!RbiY#^7Njqw z^&-5+y`%ZX9D<@MO>fPj&CrS-A1WDblB=m8*}Xl1y4E1pphlC}$Bkl_zU4q>;In2b)wz#J6FVr>B#*z6u;wF-p4n^bhdA{UJhviqzbglEsWp_ zJ8@otAIVCIma4TW-*fY36Whb%iP?B}^LdTVeAj;TWKVn+w$b)7DnZ%%rv``{ECyw5 z=|64R>L`8DYM+|>u>wO=eTncXc3rt@OP!BwP0E&!k5Jro*-PBV z9uVrytZqIsDp0@C_xMPOZj)R|6kRn}14X`yO8q%u{1Nh;aVXAj`oS z=PwMuM^=dD9TOR5qrytwWpJt%G2;0jY3b>f#TcPMH4XQ8WKTABFQ;9?_1130q=r@G?YA(KP4hi*aH?aWEAcjzWI_4#FMT!VXw7 z{>aoyRkm!QlA3N`oYhwJDK5ooWqDeqtbER1>B`7ar?+&Pu_i~C=pmh`Bl(MVQ;p`u zpAQO%^B$m7<6QXbzC%d)u^^Tl6OUE%oU35}O_X4g)){*D{`{CV%&Io_q?dc-Pb5sb zz3((-niMn3B$b+`7IU60Bpg8X|D!bb^R+9&~ZkB-)lwApSE5x zau!)+Dq1$ve%weiY;_V_*(2%W?K+QXZdw&a8}#J&U9tX;D;jC`2N;zm_w-~wn94t4 z?A8jdl=n9fi@w45HEhpmy@iu*nlVSN3Bd{3y&~`-*N)eW>{DXFGw5?qCs8gBdwguO zL`LGvFxsM57>v_bA)tPKc=Y#rYV%#MLqRo44hHqA{`d#jdNQ2XuN30n5i4sZf4e22 zTx7paT=BOp*Ny+x0^HzW?G(k5B>)>gMDo*EVO<)R zG#b%HwOp6#H6(Gf8E-2+QGDe#8>Hx-Ey1kDF0;i{(=PrgA!f>nzFOYrpy$!WO3d{f zK9`|R2e#eD(2JoPZof2Cp`dGd@#kWkYc+xL>J%MaKtA~%F+=|B?Pn4u&xPl{70}dr z%l>8_)FOYJJK7nTpkzmTO&WFReNp*xMe&P6r)6%W&`jzzVaM6+Rz2`kMvhD|C2^Y9O-zONk%=tEV=Lo-N{HFhq&>)JsR#;oY_sIG^>l2RKelMBI zKcw+(ynTKYaU^A<>yO%Iyo&h~&5YCi?s8w-{#h1Txm>N=JKcy6I4Tk7H%7W|wlQ+B zq7-!L6-=tJL3_sV37)uTij^>FJSX--%eBGI@ZerHKl6SEN!o^Y0o!yJB?b!o`R$POcaG^Bg zf)6b!A-dFjmM0yV1SYY@u`^`P!X|!NU#9gc8&e+}2(=oaE1`#lOI1C#Q}t1-Uf!#b z&MCvR63rLu?ZF`F;^g!;CuCm?vU-ivE?R{wSQpKcSEJL^eE(h4?8V;02YK>i?O3RcX6bn%f4&rUODNw>Z7A0>HuwR- z@3BidB}Z~{PuMK!&`n{^;mA_;+LC4Kb2l5Y6`lzE=X_$#mx6vTTShrFWXcTJv_+k_ z`WT`tpBkm-v6%^fM=e)b$W$l{pfgdmA@OUBA(C3oyZH_dSxLD%qelE~*GEhA$OJtF z`nbVKURqZtn<{n-ztW5euwpkAxs54fC&tNpi_In}*?{|rU!9nq!Ag+skDu6Q8gXqh z#R-2**Nsl!eIH1Cl2F5Ho_h92(U(rW=;Oe9H^yk3=e_{I_(EJ{g%bsG26dEqn&4o>Ux%KL__e|9aQ{A839J!m zN5;z{rKT%90Q%#_zE2ne^aB*?toE$E&ed;a-GmjmiM19=pyn(`Os1k8bcIj z*h6ogvXK~IC}h*NWK3K52RDHbbAQZdjd5YQL4tw)>RN+b{0#K`5>}j|l$L`SDaBf_ z2{NLu=ZJ={-YcSczb@|c*-^~SH>j-knUCVSz)EUhdKASk`qX>ca$l|~OKWp{TM~eU zNH1}fQl3iPrIGC29DhJ9G-EK}i*~5cOUCqC~t7>kVNxS5g*X$~pV)RMJ4QP4O>LIsNvB*rC z8FIZ~FsZIi`L@LFemdF%CHsIGse&3xv<7`QvE^fl=A2(53zG^H z*bJE$@8jCO-*Go@6Im zOG-c0Y_>ntugH8vhaDqLk;rZ!7B(WyY<6D!V8!FI*+QRfP2V2TT>oX2?Rjw|FcF!cCO#V~aNp{c%EYG|xi&78T!$3iR3Wxc zCktXV-B7XyRSOQ2T7Oq@N%nbtQhZZB%pvZ&nVuT?^h4Cpv1QC}V|6q3II%?s*%h4T znpgk+*=(!T5PZlVNFbV?!Ly`2rmhOBdm=98OhY! z^k{SJ7074;J;>AuTdz8)vwp!*&u!VSk{}Uz^ftu0@7Xbm_1?Vj2Ol4k-|074)GGBS zt8LWloWl?)UmeQ}YwIU=%iU=p>Eg7SPJ~0nJrGK;yPsIc^H}xz-+5GRyM%!Pf()a% zAAUF5T=y46--J>~2Hs;?ovh&ip#=)Pg1L)Df>vYPkCv9bJisI))!v4j~@r%EI*;D=P#U&9)LObK&4e;)JM@4 zMA8C6Kb2ZX7C4TbPq1oWP{@Y^+f2}!AgAh1GafO=({71JjnBo**cjhPpC6agw)%2kN*|~?KK(YPe)8lC zNUomtonRaYUE_m-GKv{CzkKm5As3oc8L|T?&fc`PRS#mMYa)i$Ebm zVP8;V#epbew}UPPkC3ocNoz^-D)mVT;ouG^58u=}Ztc69n@np}G7jq>AJ2GYgLqDO zd{AFBV|tX2IHWr3|}FN%LtOCn5J9lP11wQ z6st_&>>0L$G0h*tP`o>27GlQz@^D1B!9oYoB)J?c8=OypE(nf2St|BWu}Ii`X~d%m zPMt#-85q#Z#w1)_pTglVaqt^Bg&Zw6!3PZx7Y~RDvMd6_o3*va%T2nI_+x(ld>tuA zO-HB4onW=$qP%fDm@5ze-twVx6I;D~-ld4+WLTwGpo$#MN2ds$%%WYLZLspcQE<%q z`gI?qqlkcRN9HwyA}szBF6HCW+7IFZkJ=JrX1x9-jcB?RATb21WwRLP?COIvdN{nj zK|~ZIN0QQB01*lceCo6vl#p;AVq>m{XC@PrQ|{+mRo(GifuIfChlBKcrW5nK({4K@ zaMX{8R6vWcHdaOl3d7oh6`g_^Q1{^D;msDGcij_aH#!EV&(~^92Eh&pXx=wAdL`TO zL7amaZyu~@zdZ?p0AkRstd3VOshT0`7DOckdNq)QGJWCRhl2SYK6(UR&JG%!EYHicXwRqit4+fNYH(;y1#Xv_ zNzH9O`T{ls1bSKUF5wb!F$MT5e8}S5C(5sI#Q&o0xpJvKdUJC#991JaGSJ-dd0hzr zf-HjQr&8eg!739i?MEE)r^=5F+)w5{y=X&iJ=t5x)vSLyQlw=BhWOdq`un?sSy$Zo zjOTeUm=F<>B0|>|TtW38ZgWSMM-x_X(cI1suJ>>}63<`0;DKDX8?;2b`}>G$7*ti; z^~ajx%^N>9V?f-8JQ>KLKoHP*@0Dkfye4SOBnyIddO(>m21rdC@tNY8tFk3&@jW%o z9sIWy049(EK7IOh3l$X=)UMW77cQPBbGIN;PiB2^oiFx&q4GMc697PEfavV+#t5sL zAm|3nr@lws=dtXsFjE4}On2~op4-^i28-=s3VDjy-mDELAK;9?zeMjXs6YC^w!oFs ztY#Wc&dyY~aA$u}dS!xx!ObZ_3))|9A`j^Vw4@TrZ2ajUZcK#T22D~A2pYYEMod6^ z3Oc&)PCHT%YkYRgK|K>fZ4Fj`zGBxp?JPssBhp3?K;8itxVk(?6l(Qu$2YYB%@D~q zJTVH%xyNdMnjdKy^+J~kh;l&F>H|7H>wlNWdYq)E^MS0!6O}9=1by`MX*?*Z?&9Hj z%XOM2Wb7Xu8Ny~or%*c2qEa}|zBiu$UCYeAms*v_YTBpL%jZUXMLg5akNWRSp*q(g|RCe3Nc3rJEHPxF_wK2Q9)?Iy|bpgi!f%ebodN&sc-Z(xxTF_}T ztCafQdGrQ_z_bwzz-~SJBAQjJm(uH^87dk+xUcun2!oN}aAgJeM=tOR!~WElh!h?P zEl`ZzAtZdKZO%7C7qaey`+QdG-x(3`f`w0%o=qU70)go4;-YU1luJ@l(JS9Q&K+UJ zV_-Yb+bu!Jx9PK^l2klFyLN39B#*anDfB^-oUc}e1JbU$ckjl+8o!ieu79|JiRh1j zEf|3Q6T#mLNE*?qF~etQ00ES-oF;c+$!uW2S%e$`pu4nf<}fN121P_fEIn9{kba(~ z)#$l7)0mQzL+^UL-2H6SN zO%HS4^gbO0mBlO&wRcwo>>&|!n_GZJKge~Ppk%`X9F{^KN|DEke9M$dnjPKdl4 zLfjYv83llR4ss*ti~>RLub8j=61dUYP#%$9TaeDsw|DmIgP)t4Uc3n+)`^>#HwI+w z1Or&{37vysop+mWp`L(d5@4~kdkpFX4CH=cZz<-0F=c_S%pI`iMH|^FDOzJHs{4U2 zEzk`Ap*D?ZdG*LkKfBQ+&RYKy6#gfDURP*MK#rW3qLi4Op5v17enIdTRtj0q@1AV0i%oE*9}b$Bp40TjA^MIHX>uOEKzBIds(2 z+E0jcluI5Wy%LALrNyPCR(N>tAa-fs3mwBpppBgekO7rh^+7NHSc6CH5I0OXBxv%4 zH3E|Q0H0o&xB{YLP+R)Qa>jzL7SRHO`He2m4iTS%GA5&y;ouiMqw0kWKi2r zKJ?aMxz0ABg3!<)?hFF@^-P1uSfiI9$Wz;fhN55$W}HA85fOfVte@!6DX=iVu<#1J z3>6tb0A+ERy5-T~VXHa!ip!hvJ0J>-Rnm0vJ6P#kn4cF?P>5Xm=m${=uK#80=1p*R zWWFZ(nOiA&$*t?x7vpOqOhC#R{S%Y@NCheYX5rik$c~2i8s12eHJt$gaid9}ozS!q z30cs>s^a7T#n#TXFy3<^M#0d39V?nS$^u#cylQkI+m?&ou}lOMu>1acXKT3177-DgC!2l;&$ z*vWnq8tyJk1|i8?PEHOqBO83Js@*g{Y4www;O5H)Mc~ zn1_-)cduTmm#=lSK>T`psut11x}C#KEqCxblP07bopz=rMMQ4H)Q$bda4?L0EUVmU z)@NUe--$T=rEHdDq_+HNpsTBExkf0i!(KD!O~z0Pxk?n{JA@PhMQDMc4geRG$6C|X zHn1{M{RDA7a9Nl<5OQ^OExh~^85z0a$-L_D4WO`Q|7y%Hl_!SBiH9K?d_d}6W--C-xINhcy6(8A4vhG;62(t7RoGni^d=1jB{|vCjX#5+7O39mz(BqEpPwZXdBZ@|XbbZuYU4+WSF{%=3!%}u_E~HV ziTine@kC}jNu^f}cMT>iv;bv2pFzE@2Nxp<1=Cvsq1@nuzaX76JDJ1FNx_b+IgYJ>q?h)XJOiQiCmiy0@N$~n&485O#^uxxynF0IG0U{ZD=oS} zqRDdp7sxz9`n(TE80gF`c*2)H13wAxOvDG9~p-s7ARA7 zVH*$zZND>}>54#ohWmW6pB+~`W+4dug7Pxcq55@J03<1KKea`eGo%b@L?t|sDO%Y#2LvGwT1xLP4MLJmlkO7{{Q`wN%S=+pRlI(u zI|Y>Bh(SO@jObN?8`|}}W$mu?ivs;8h?AFYwhY|U(t&!_Df(DSLIMj$d`c!k5F*L@ zb#``Em(@;1b?PW?s&=O#Ay+3%%8k~=^z+VL1qAepQ%8mqFsxe4HNzmpAhg}8Y zapvB)Z1^tra(`4W)CL$e2ht$nGHZh*$AX?w@&D{Km~nSNoYiKvp9+Y=7)*8jyE<;f zBx8N{?AgRQb&>eLkW^Tfz}`>%lk;;Jn`?namGgcF-TNT^2MIi2E#Mpq-b&*emK06|Y=gELxRk_7PH2By&wDCYa z4FjG=Fv!Kr&z})l`WKZX217$#o%z6H0wzvOO&I~fVY-kMnT15s)x5kIB6I(ykQ-h= z*`2fC|Wk36q}>o;-On zv9tt3DEm-H&Mz;2Y}TFyszysq{d0g@_vdYJamcv~uxHvpmS40P%t!0Bv=x@z#ZCM<6<^nf?ECZ0C%^p|1({N4SsM&Nta??fcAs_S{O7nrxcINGG!PQ5%#yVZNR zyPJ=D0uMtvpo@$8+px2mu4^=~dDlUpRS3NbC;$;IjZDls?`lJP1D1AiKJ%~AJ!T4K zBavIdbODS6_IUj}*8&>T3LLK5dhQz1qk}>U>Q$KvQ^@vmy9Wn)yR*%iU%$fUc0mvc z!n6X0e)mv!o?v@*CUEOx4)f6`&jDQj0b8wjC0%hlY)`tF zLUCKqk)rj|-NVBK#%G`bWxqDyC!6tRZhbufdOXky|_(F?87-kR4$OWRmp0I0KL30s0g)(BlzrADXLM@ZS zu(Gm(H~b{ha&L}h(sw)A!in>o;*_0% zZD=Avo$(pgMz~g~atW!B({#`us`Y8p*sS=9og(#}$^QQSJE|K+rBbG>7)W=(k4O`# zV4-IPjkNc$nJFGeB=7^Kff6w>z(29vTd#zK6z@6AK;qkDhMxG^@uXd-ne4HKs(P(s zFu+M_q$$bWyK;-Su$FWvpMIP7+(L!XF#CKMalz)mA1^(C4Z-+-mun_3Y!5u-T9Sq z?nX~L3>=)VP^H0`bBWurrRhjv5449xq2GBMUQj7BL{b{GSGrKWpr=z%8AUtX&?uHq zZwOadJ2=qL)B8jGmq7^(z&2O>xeza88G7E8t}f+DMVeXLUEfbBq&3+VO1puF@QQqoRf z?lEQ)7iT>i4PnSU4k@V^Skz^!VkDNsD8#^^3~EOX=n6w~@E24g9RNEl@_YMcc9DM7 zV$5R>j*c+<)Sv@(2-2~K;5A^nL+eYg=``gKGjv+cXZ8I~*35)eV{l%cdNrP3mH8Mu zoK#^<(OPQ2d?|FKkZ4<3`32Sw2@DiZo`7L;5^zlz=&XSeMTnBB$oq9ko^O$wbC?sh zu513q7g@{4WuC|7CVy_@;u^tv6(`uuUdK4ne4h-9h>$PrxD@gamn~4`5;g83hMT#4 zdO#Lg5p_uBF;qWb3gi;nH7QW!;b#0cRxze6+P609OE!Sygmn5Km|^&RpXHHKtY_I{ z#V|Y6g2aj%=(9=K+e3vO(zF+i0TX>xzSa+*Q39380knspw@&f=bP+#2J$;|~Ms#v= zFZ7*=pW4$y?nWjPfmX~oHh$r6?pcTN^D)ooo)^_i%WupqLSFpOF@(Ra{uAO@ZVOTv zzN2AdyOTu#fH!73PDeun6I-Iv((uiVjNc+qW*`k&aJ$~he%a;98;5SN-{SRu|C#Mv zsoERqSw{DeMsKJ;z3=sD(EoGTj#M{;+!dJ$q z07yNNeJe_B+wsS9b1#G6ylU0m>$wOC4IQ$qa&UG1mXYzu;c3!Ho?NZ2XmRf7Axqa8 zH$~{5KjJ*p(FV^%_g}?dePUZacNXxRY59n5pc0M#Vb)0GkC*>5iEm%}G+*LjxzEJx zd^#kQ%zkkDrcSR_5D5f`ByGf#n3vr_Y-ye$;q8?chv%2UCFb0<1H!*;$oN9a*bPr( z2A4`|msz637^B3(GZphH?w*&4FV4-SF-CQ^xj43lYZr_vy075^Cd1{kMORg@`9JY z3YFz#Hm{+eTx6S8kUC-f+dL+pX$+>hQN#vsdQd^{h>C*pMU?>g%^@Nz+i<1#Yk0(t z0|A$0A}7YtM~%t88m~$)QBcB{0}WK-sw0}F=X4z4>i_f4gPVO}B6!YbA1WRqKNc01 LdR-`_{o(%t=de2u literal 13740 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 T6Dz{kuMjE<8uF#GkAwaXg2b$$ diff --git a/docs/aggregate__across__genes_8hpp_source.html b/docs/aggregate__across__genes_8hpp_source.html index 1949123..2e1a939 100644 --- a/docs/aggregate__across__genes_8hpp_source.html +++ b/docs/aggregate__across__genes_8hpp_source.html @@ -99,313 +99,297 @@
7#include <stdexcept>
8
9#include "tatami/tatami.hpp"
-
10
-
16namespace scran_aggregate {
-
17
-
- -
26 int num_threads = 1;
-
27
-
32 bool average = false;
-
33};
+
10#include "tatami_stats/tatami_stats.hpp"
+
11
+
17namespace scran_aggregate {
+
18
+
+ +
27 int num_threads = 1;
+
28
+
33 bool average = false;
+
34};
-
34
-
39template <typename Sum_>
-
- -
46 std::vector<Sum_*> sum;
-
47};
+
35
+
40template <typename Sum_>
+
+ +
47 std::vector<Sum_*> sum;
+
48};
-
48
-
53template <typename Sum_>
-
- -
60 std::vector<std::vector<Sum_> > sum;
-
61};
+
49
+
54template <typename Sum_>
+
+ +
61 std::vector<std::vector<Sum_> > sum;
+
62};
-
62
-
66namespace aggregate_across_genes_internal {
-
67
-
68template<typename Index_, typename Gene_, typename Weight_>
-
69std::vector<Gene_> create_subset(const std::vector<std::tuple<size_t, const Gene_*, const Weight_*> >& gene_sets, Index_ nrow) {
-
70 std::unordered_set<Gene_> of_interest;
-
71 for (const auto& set : gene_sets) {
-
72 auto set_size = std::get<0>(set);
-
73 auto set_genes = std::get<1>(set);
-
74 of_interest.insert(set_genes, set_genes + set_size);
-
75 }
-
76
-
77 std::vector<Index_> subset(of_interest.begin(), of_interest.end());
-
78 if (!subset.empty()) {
-
79 std::sort(subset.begin(), subset.end());
-
80 if (subset.front() < 0 || subset.back() >= nrow) {
-
81 throw std::runtime_error("set indices are out of range");
-
82 }
-
83 }
-
84
-
85 return subset;
-
86}
-
87
-
88template<typename Index_>
-
89std::pair<std::vector<Index_>, Index_> create_subset_mapping(const std::vector<Index_>& subset) {
-
90 Index_ offset = 0;
-
91 size_t span = subset.back() - offset + 1;
-
92 std::vector<Index_> mapping(span);
-
93 size_t nsubs = subset.size();
-
94 for (size_t i = 0; i < nsubs; ++i) {
-
95 mapping[subset[i] - offset] = i;
-
96 }
-
97 return std::make_pair(std::move(mapping), offset);
-
98}
-
99
-
100template<typename Data_, typename Index_, typename Gene_, typename Weight_, typename Sum_>
-
101void compute_aggregate_by_column(
- -
103 const std::vector<std::tuple<size_t, const Gene_*, const Weight_*> >& gene_sets,
-
104 const AggregateAcrossGenesBuffers<Sum_>& buffers,
-
105 const AggregateAcrossGenesOptions& options)
-
106{
-
107 // Identifying the subset of rows that actually need to be extracted.
-
108 tatami::VectorPtr<Index_> subset_of_interest = std::make_shared<std::vector<Index_> >(create_subset<Index_>(gene_sets, p.nrow()));
-
109 const auto& subset = *subset_of_interest;
-
110 size_t nsubs = subset.size();
-
111
-
112 // Creating a mapping back to the gene indices in the subset.
-
113 const size_t num_sets = gene_sets.size();
-
114 std::vector<std::pair<std::vector<Index_>, const Weight_*> > remapping(num_sets);
-
115 if (nsubs) {
-
116 auto sub_mapping = create_subset_mapping(subset);
-
117 const auto& mapping = sub_mapping.first;
-
118 Gene_ offset = sub_mapping.second;
-
119
-
120 for (size_t s = 0; s < num_sets; ++s) {
-
121 const auto& set = gene_sets[s];
-
122 auto set_size = std::get<0>(set);
-
123 auto set_genes = std::get<1>(set);
-
124
-
125 auto& remapped = remapping[s].first;
-
126 remapped.reserve(set_size);
-
127 for (size_t g = 0; g < set_size; ++g) {
-
128 remapped.push_back(mapping[set_genes[g] - offset]);
-
129 }
-
130 remapping[s].second = std::get<2>(set);
-
131 }
-
132 }
-
133
-
134 tatami::parallelize([&](size_t, Index_ start, Index_ length) {
-
135 // We extract as sparse even if it is dense, as it's just
-
136 // easier to index from a dense vector.
-
137 auto ext = tatami::consecutive_extractor<false>(&p, false, start, length, subset_of_interest);
-
138 std::vector<Data_> vbuffer(nsubs);
-
139
-
140 for (Index_ x = start, end = start + length; x < end; ++x) {
-
141 auto ptr = ext->fetch(vbuffer.data());
-
142 for (size_t s = 0; s < num_sets; ++s) {
-
143 const auto& set = remapping[s];
-
144
-
145 Sum_ value = 0;
-
146 if (set.second) {
-
147 for (size_t i = 0, send = set.first.size(); i < send; ++i) {
-
148 value += ptr[set.first[i]] * set.second[i];
-
149 }
-
150 } else {
-
151 for (auto ix : set.first) {
-
152 value += ptr[ix];
-
153 }
-
154 }
-
155
-
156 buffers.sum[s][x] = value;
-
157 }
-
158 }
-
159
-
160 }, p.ncol(), options.num_threads);
-
161}
-
162
-
163template<typename Data_, typename Index_, typename Gene_, typename Weight_, typename Sum_>
-
164void compute_aggregate_by_row(
- -
166 const std::vector<std::tuple<size_t, const Gene_*, const Weight_*> >& gene_sets,
-
167 const AggregateAcrossGenesBuffers<Sum_>& buffers,
-
168 const AggregateAcrossGenesOptions& options)
-
169{
-
170 // Identifying the subset of rows that actually need to be extracted.
-
171 auto subset = create_subset<Index_>(gene_sets, p.nrow());
-
172 size_t nsubs = subset.size();
-
173 auto sub_oracle = std::make_shared<tatami::FixedViewOracle<Index_> >(subset.data(), nsubs);
-
174
-
175 const size_t num_sets = gene_sets.size();
-
176 std::vector<std::vector<std::pair<size_t, Weight_> > > remapping(nsubs);
-
177 if (nsubs) {
-
178 auto sub_mapping = create_subset_mapping(subset);
-
179 const auto& mapping = sub_mapping.first;
-
180 Gene_ offset = sub_mapping.second;
-
181
-
182 for (size_t s = 0; s < num_sets; ++s) {
-
183 const auto& set = gene_sets[s];
-
184 auto set_size = std::get<0>(set);
-
185 auto set_genes = std::get<1>(set);
-
186 auto set_weights = std::get<2>(set);
-
187
-
188 if (set_weights) {
-
189 for (size_t g = 0; g < set_size; ++g) {
-
190 remapping[mapping[set_genes[g] - offset]].emplace_back(s, set_weights[g]);
-
191 }
-
192 } else {
-
193 for (size_t g = 0; g < set_size; ++g) {
-
194 remapping[mapping[set_genes[g] - offset]].emplace_back(s, 1);
-
195 }
-
196 }
-
197 }
-
198 }
-
199
-
200 tatami::parallelize([&](size_t t, Index_ start, Index_ length) {
-
201 std::vector<std::vector<Data_> > local_buffers;
-
202 if (t != 0) {
-
203 // Creating local buffers to protect against false sharing in t > 0.
-
204 local_buffers.reserve(num_sets);
-
205 for (size_t s = 0; s < num_sets; ++s) {
-
206 local_buffers.emplace_back(length);
-
207 }
-
208 } else {
-
209 // We still use the output buffers to write when t == 0, to avoid
-
210 // penalizing the serial case where no false sharing can occur. This
-
211 // requires zeroing for consistency with the local_buffers.
-
212 for (size_t s = 0; s < num_sets; ++s) {
-
213 std::fill_n(buffers.sum[s] + start, length, static_cast<Sum_>(0));
-
214 }
-
215 }
-
216
-
217 if (p.sparse()) {
-
218 auto ext = tatami::new_extractor<true, true>(&p, true, sub_oracle, start, length);
-
219 std::vector<Data_> vbuffer(length);
-
220 std::vector<Index_> ibuffer(length);
+
63
+
67namespace aggregate_across_genes_internal {
+
68
+
69template<typename Index_, typename Gene_, typename Weight_>
+
70std::vector<Gene_> create_subset(const std::vector<std::tuple<size_t, const Gene_*, const Weight_*> >& gene_sets, Index_ nrow) {
+
71 std::unordered_set<Gene_> of_interest;
+
72 for (const auto& set : gene_sets) {
+
73 auto set_size = std::get<0>(set);
+
74 auto set_genes = std::get<1>(set);
+
75 of_interest.insert(set_genes, set_genes + set_size);
+
76 }
+
77
+
78 std::vector<Index_> subset(of_interest.begin(), of_interest.end());
+
79 if (!subset.empty()) {
+
80 std::sort(subset.begin(), subset.end());
+
81 if (subset.front() < 0 || subset.back() >= nrow) {
+
82 throw std::runtime_error("set indices are out of range");
+
83 }
+
84 }
+
85
+
86 return subset;
+
87}
+
88
+
89template<typename Index_>
+
90std::pair<std::vector<Index_>, Index_> create_subset_mapping(const std::vector<Index_>& subset) {
+
91 Index_ offset = 0;
+
92 size_t span = subset.back() - offset + 1;
+
93 std::vector<Index_> mapping(span);
+
94 size_t nsubs = subset.size();
+
95 for (size_t i = 0; i < nsubs; ++i) {
+
96 mapping[subset[i] - offset] = i;
+
97 }
+
98 return std::make_pair(std::move(mapping), offset);
+
99}
+
100
+
101template<typename Data_, typename Index_, typename Gene_, typename Weight_, typename Sum_>
+
102void compute_aggregate_by_column(
+ +
104 const std::vector<std::tuple<size_t, const Gene_*, const Weight_*> >& gene_sets,
+
105 const AggregateAcrossGenesBuffers<Sum_>& buffers,
+
106 const AggregateAcrossGenesOptions& options)
+
107{
+
108 // Identifying the subset of rows that actually need to be extracted.
+
109 tatami::VectorPtr<Index_> subset_of_interest = std::make_shared<std::vector<Index_> >(create_subset<Index_>(gene_sets, p.nrow()));
+
110 const auto& subset = *subset_of_interest;
+
111 size_t nsubs = subset.size();
+
112
+
113 // Creating a mapping back to the gene indices in the subset.
+
114 const size_t num_sets = gene_sets.size();
+
115 std::vector<std::pair<std::vector<Index_>, const Weight_*> > remapping(num_sets);
+
116 if (nsubs) {
+
117 auto sub_mapping = create_subset_mapping(subset);
+
118 const auto& mapping = sub_mapping.first;
+
119 Gene_ offset = sub_mapping.second;
+
120
+
121 for (size_t s = 0; s < num_sets; ++s) {
+
122 const auto& set = gene_sets[s];
+
123 auto set_size = std::get<0>(set);
+
124 auto set_genes = std::get<1>(set);
+
125
+
126 auto& remapped = remapping[s].first;
+
127 remapped.reserve(set_size);
+
128 for (size_t g = 0; g < set_size; ++g) {
+
129 remapped.push_back(mapping[set_genes[g] - offset]);
+
130 }
+
131 remapping[s].second = std::get<2>(set);
+
132 }
+
133 }
+
134
+
135 tatami::parallelize([&](size_t, Index_ start, Index_ length) {
+
136 // We extract as sparse even if it is dense, as it's just
+
137 // easier to index from a dense vector.
+
138 auto ext = tatami::consecutive_extractor<false>(&p, false, start, length, subset_of_interest);
+
139 std::vector<Data_> vbuffer(nsubs);
+
140
+
141 for (Index_ x = start, end = start + length; x < end; ++x) {
+
142 auto ptr = ext->fetch(vbuffer.data());
+
143 for (size_t s = 0; s < num_sets; ++s) {
+
144 const auto& set = remapping[s];
+
145
+
146 Sum_ value = 0;
+
147 if (set.second) {
+
148 for (size_t i = 0, send = set.first.size(); i < send; ++i) {
+
149 value += ptr[set.first[i]] * set.second[i];
+
150 }
+
151 } else {
+
152 for (auto ix : set.first) {
+
153 value += ptr[ix];
+
154 }
+
155 }
+
156
+
157 buffers.sum[s][x] = value;
+
158 }
+
159 }
+
160
+
161 }, p.ncol(), options.num_threads);
+
162}
+
163
+
164template<typename Data_, typename Index_, typename Gene_, typename Weight_, typename Sum_>
+
165void compute_aggregate_by_row(
+ +
167 const std::vector<std::tuple<size_t, const Gene_*, const Weight_*> >& gene_sets,
+
168 const AggregateAcrossGenesBuffers<Sum_>& buffers,
+
169 const AggregateAcrossGenesOptions& options)
+
170{
+
171 // Identifying the subset of rows that actually need to be extracted.
+
172 auto subset = create_subset<Index_>(gene_sets, p.nrow());
+
173 size_t nsubs = subset.size();
+
174 auto sub_oracle = std::make_shared<tatami::FixedViewOracle<Index_> >(subset.data(), nsubs);
+
175
+
176 const size_t num_sets = gene_sets.size();
+
177 std::vector<std::vector<std::pair<size_t, Weight_> > > remapping(nsubs);
+
178 if (nsubs) {
+
179 auto sub_mapping = create_subset_mapping(subset);
+
180 const auto& mapping = sub_mapping.first;
+
181 Gene_ offset = sub_mapping.second;
+
182
+
183 for (size_t s = 0; s < num_sets; ++s) {
+
184 const auto& set = gene_sets[s];
+
185 auto set_size = std::get<0>(set);
+
186 auto set_genes = std::get<1>(set);
+
187 auto set_weights = std::get<2>(set);
+
188
+
189 if (set_weights) {
+
190 for (size_t g = 0; g < set_size; ++g) {
+
191 remapping[mapping[set_genes[g] - offset]].emplace_back(s, set_weights[g]);
+
192 }
+
193 } else {
+
194 for (size_t g = 0; g < set_size; ++g) {
+
195 remapping[mapping[set_genes[g] - offset]].emplace_back(s, 1);
+
196 }
+
197 }
+
198 }
+
199 }
+
200
+
201 tatami::parallelize([&](size_t t, Index_ start, Index_ length) {
+
202 auto get_sum = [&](Index_ i) -> Sum_* { return buffers.sum[i]; };
+
203 tatami_stats::LocalOutputBuffers<Sum_, decltype(get_sum)> local_sums(t, num_sets, start, length, std::move(get_sum));
+
204
+
205 if (p.sparse()) {
+
206 auto ext = tatami::new_extractor<true, true>(&p, true, sub_oracle, start, length);
+
207 std::vector<Data_> vbuffer(length);
+
208 std::vector<Index_> ibuffer(length);
+
209
+
210 for (size_t sub = 0; sub < nsubs; ++sub) {
+
211 auto range = ext->fetch(vbuffer.data(), ibuffer.data());
+
212
+
213 for (const auto& sw : remapping[sub]) {
+
214 auto outptr = local_sums.data(sw.first);
+
215 auto wt = sw.second;
+
216 for (Index_ c = 0; c < range.number; ++c) {
+
217 outptr[range.index[c] - start] += range.value[c] * wt;
+
218 }
+
219 }
+
220 }
221
-
222 for (size_t sub = 0; sub < nsubs; ++sub) {
-
223 auto range = ext->fetch(vbuffer.data(), ibuffer.data());
-
224 for (const auto& sw : remapping[sub]) {
-
225 auto wt = sw.second;
-
226 auto outptr = (t != 0 ? local_buffers[sw.first].data() : buffers.sum[sw.first] + start);
-
227 for (Index_ c = 0; c < range.number; ++c) {
-
228 outptr[range.index[c] - start] += range.value[c] * wt;
-
229 }
-
230 }
-
231 }
-
232
-
233 } else {
-
234 auto ext = tatami::new_extractor<false, true>(&p, true, sub_oracle, start, length);
-
235 std::vector<Data_> vbuffer(length);
-
236
-
237 for (size_t sub = 0; sub < nsubs; ++sub) {
-
238 auto ptr = ext->fetch(vbuffer.data());
-
239 for (const auto& sw : remapping[sub]) {
-
240 auto outptr = (t != 0 ? local_buffers[sw.first].data() : buffers.sum[sw.first] + start);
-
241 auto wt = sw.second;
-
242 for (Index_ cell = 0; cell < length; ++cell) {
-
243 outptr[cell] += ptr[cell] * wt;
-
244 }
-
245 }
-
246 }
-
247 }
-
248
-
249 if (t != 0) {
-
250 for (size_t s = 0; s < num_sets; ++s) {
-
251 const auto& current = local_buffers[s];
-
252 std::copy(current.begin(), current.end(), buffers.sum[s] + start);
-
253 }
-
254 }
-
255 }, p.ncol(), options.num_threads);
-
256}
-
257
-
258}
-
283template<typename Data_, typename Index_, typename Gene_, typename Weight_, typename Sum_>
-
- - -
286 const std::vector<std::tuple<size_t, const Gene_*, const Weight_*> >& gene_sets,
- -
288 const AggregateAcrossGenesOptions& options)
-
289{
-
290 if (input.prefer_rows()) {
-
291 aggregate_across_genes_internal::compute_aggregate_by_row(input, gene_sets, buffers, options);
-
292 } else {
-
293 aggregate_across_genes_internal::compute_aggregate_by_column(input, gene_sets, buffers, options);
-
294 }
+
222 } else {
+
223 auto ext = tatami::new_extractor<false, true>(&p, true, sub_oracle, start, length);
+
224 std::vector<Data_> vbuffer(length);
+
225
+
226 for (size_t sub = 0; sub < nsubs; ++sub) {
+
227 auto ptr = ext->fetch(vbuffer.data());
+
228 for (const auto& sw : remapping[sub]) {
+
229 auto outptr = local_sums.data(sw.first);
+
230 auto wt = sw.second;
+
231 for (Index_ cell = 0; cell < length; ++cell) {
+
232 outptr[cell] += ptr[cell] * wt;
+
233 }
+
234 }
+
235 }
+
236 }
+
237
+
238 local_sums.transfer();
+
239 }, p.ncol(), options.num_threads);
+
240}
+
241
+
242}
+
267template<typename Data_, typename Index_, typename Gene_, typename Weight_, typename Sum_>
+
+ + +
270 const std::vector<std::tuple<size_t, const Gene_*, const Weight_*> >& gene_sets,
+ +
272 const AggregateAcrossGenesOptions& options)
+
273{
+
274 if (input.prefer_rows()) {
+
275 aggregate_across_genes_internal::compute_aggregate_by_row(input, gene_sets, buffers, options);
+
276 } else {
+
277 aggregate_across_genes_internal::compute_aggregate_by_column(input, gene_sets, buffers, options);
+
278 }
+
279
+
280 if (options.average) {
+
281 size_t nsets = gene_sets.size();
+
282 tatami::parallelize([&](int, size_t start, size_t length) {
+
283 size_t NC = input.ncol();
+
284 for (size_t s = start, end = start + length; s < end; ++s) {
+
285 const auto& set = gene_sets[s];
+
286 auto set_size = std::get<0>(set);
+
287
+
288 Sum_ denom = 0;
+
289 auto set_weights = std::get<2>(set);
+
290 if (set_weights) {
+
291 denom = std::accumulate(set_weights, set_weights + set_size, static_cast<Sum_>(0));
+
292 } else {
+
293 denom = set_size;
+
294 }
295
-
296 if (options.average) {
-
297 size_t nsets = gene_sets.size();
-
298 tatami::parallelize([&](int, size_t start, size_t length) {
-
299 size_t NC = input.ncol();
-
300 for (size_t s = start, end = start + length; s < end; ++s) {
-
301 const auto& set = gene_sets[s];
-
302 auto set_size = std::get<0>(set);
-
303
-
304 Sum_ denom = 0;
-
305 auto set_weights = std::get<2>(set);
-
306 if (set_weights) {
-
307 denom = std::accumulate(set_weights, set_weights + set_size, static_cast<Sum_>(0));
-
308 } else {
-
309 denom = set_size;
-
310 }
-
311
-
312 auto current = buffers.sum[s];
-
313 for (size_t c = 0; c < NC; ++c) {
-
314 current[c] /= denom;
-
315 }
-
316 }
-
317 }, nsets, options.num_threads);
-
318 }
-
319}
+
296 auto current = buffers.sum[s];
+
297 for (size_t c = 0; c < NC; ++c) {
+
298 current[c] /= denom;
+
299 }
+
300 }
+
301 }, nsets, options.num_threads);
+
302 }
+
303}
-
320
-
340template<typename Sum_ = double, typename Data_, typename Index_, typename Gene_, typename Weight_>
-
- - -
343 const std::vector<std::tuple<size_t, const Gene_*, const Weight_*> >& gene_sets,
-
344 const AggregateAcrossGenesOptions& options)
-
345{
- - -
348
-
349 size_t NC = input.ncol();
-
350 size_t nsets = gene_sets.size();
-
351 output.sum.resize(nsets);
-
352 buffers.sum.resize(nsets);
-
353
-
354 for (size_t s = 0; s < nsets; ++s) {
-
355 output.sum[s].resize(NC
-
356#ifdef SCRAN_AGGREGATE_TEST_INIT
-
357 , SCRAN_AGGREGATE_TEST_INIT
-
358#endif
-
359 );
-
360 buffers.sum[s] = output.sum[s].data();
-
361 }
-
362
-
363 aggregate_across_genes(input, gene_sets, buffers, options);
-
364 return output;
-
365}
+
304
+
324template<typename Sum_ = double, typename Data_, typename Index_, typename Gene_, typename Weight_>
+
+ + +
327 const std::vector<std::tuple<size_t, const Gene_*, const Weight_*> >& gene_sets,
+
328 const AggregateAcrossGenesOptions& options)
+
329{
+ + +
332
+
333 size_t NC = input.ncol();
+
334 size_t nsets = gene_sets.size();
+
335 output.sum.resize(nsets);
+
336 buffers.sum.resize(nsets);
+
337
+
338 for (size_t s = 0; s < nsets; ++s) {
+
339 output.sum[s].resize(NC
+
340#ifdef SCRAN_AGGREGATE_TEST_INIT
+
341 , SCRAN_AGGREGATE_TEST_INIT
+
342#endif
+
343 );
+
344 buffers.sum[s] = output.sum[s].data();
+
345 }
+
346
+
347 aggregate_across_genes(input, gene_sets, buffers, options);
+
348 return output;
+
349}
-
366
-
367}
-
368
-
369#endif
+
350
+
351}
+
352
+
353#endif
virtual Index_ ncol() const=0
virtual Index_ nrow() const=0
virtual bool prefer_rows() const=0
virtual std::unique_ptr< MyopicSparseExtractor< Value_, Index_ > > sparse(bool row, const Options &opt) const=0
-
Aggregate single-cell expression values.
Definition aggregate_across_cells.hpp:14
-
void aggregate_across_genes(const tatami::Matrix< Data_, Index_ > &input, const std::vector< std::tuple< size_t, const Gene_ *, const Weight_ * > > &gene_sets, const AggregateAcrossGenesBuffers< Sum_ > &buffers, const AggregateAcrossGenesOptions &options)
Definition aggregate_across_genes.hpp:284
+
Aggregate single-cell expression values.
Definition aggregate_across_cells.hpp:15
+
void aggregate_across_genes(const tatami::Matrix< Data_, Index_ > &input, const std::vector< std::tuple< size_t, const Gene_ *, const Weight_ * > > &gene_sets, const AggregateAcrossGenesBuffers< Sum_ > &buffers, const AggregateAcrossGenesOptions &options)
Definition aggregate_across_genes.hpp:268
void parallelize(Function_ fun, Index_ tasks, int threads)
std::shared_ptr< const std::vector< Index_ > > VectorPtr
auto consecutive_extractor(const Matrix< Value_, Index_ > *mat, bool row, Index_ iter_start, Index_ iter_length, Args_ &&... args)
-
Buffers for aggregate_across_genes().
Definition aggregate_across_genes.hpp:40
-
std::vector< Sum_ * > sum
Definition aggregate_across_genes.hpp:46
-
Options for aggregate_across_genes().
Definition aggregate_across_genes.hpp:21
-
bool average
Definition aggregate_across_genes.hpp:32
-
int num_threads
Definition aggregate_across_genes.hpp:26
-
Results of aggregate_across_genes().
Definition aggregate_across_genes.hpp:54
-
std::vector< std::vector< Sum_ > > sum
Definition aggregate_across_genes.hpp:60
+
Buffers for aggregate_across_genes().
Definition aggregate_across_genes.hpp:41
+
std::vector< Sum_ * > sum
Definition aggregate_across_genes.hpp:47
+
Options for aggregate_across_genes().
Definition aggregate_across_genes.hpp:22
+
bool average
Definition aggregate_across_genes.hpp:33
+
int num_threads
Definition aggregate_across_genes.hpp:27
+
Results of aggregate_across_genes().
Definition aggregate_across_genes.hpp:55
+
std::vector< std::vector< Sum_ > > sum
Definition aggregate_across_genes.hpp:61
diff --git a/docs/clean__factor_8hpp_source.html b/docs/clean__factor_8hpp_source.html index 3a9db58..fa597c9 100644 --- a/docs/clean__factor_8hpp_source.html +++ b/docs/clean__factor_8hpp_source.html @@ -140,7 +140,7 @@
68}
69
70#endif
-
Aggregate single-cell expression values.
Definition aggregate_across_cells.hpp:14
+
Aggregate single-cell expression values.
Definition aggregate_across_cells.hpp:15
std::vector< Factor_ > clean_factor(size_t n, const Factor_ *factor, Output_ *cleaned)
Definition clean_factor.hpp:33
diff --git a/docs/combine__factors_8hpp_source.html b/docs/combine__factors_8hpp_source.html index 7ba081c..869cec5 100644 --- a/docs/combine__factors_8hpp_source.html +++ b/docs/combine__factors_8hpp_source.html @@ -255,7 +255,7 @@
206
207#endif
Clean up a categorical factor.
-
Aggregate single-cell expression values.
Definition aggregate_across_cells.hpp:14
+
Aggregate single-cell expression values.
Definition aggregate_across_cells.hpp:15
std::vector< std::vector< Factor_ > > combine_factors_unused(size_t n, const std::vector< std::pair< const Factor_ *, Number_ > > &factors, Combined_ *combined)
Definition combine_factors.hpp:146
std::vector< Factor_ > clean_factor(size_t n, const Factor_ *factor, Output_ *cleaned)
Definition clean_factor.hpp:33
std::vector< std::vector< Factor_ > > combine_factors(size_t n, const std::vector< const Factor_ * > &factors, Combined_ *combined)
Definition combine_factors.hpp:40
diff --git a/docs/index.html b/docs/index.html index 2fc0162..9555821 100644 --- a/docs/index.html +++ b/docs/index.html @@ -98,9 +98,9 @@

Quick start

res.sums[0]; // vector of sums for the first group across genes.
res.detected; // vector of vectors of the number of detected cells per gene.
-
void aggregate_across_cells(const tatami::Matrix< Data_, Index_ > &input, const Factor_ *factor, const AggregateAcrossCellsBuffers< Sum_, Detected_ > &buffers, const AggregateAcrossCellsOptions &options)
Definition aggregate_across_cells.hpp:285
+
void aggregate_across_cells(const tatami::Matrix< Data_, Index_ > &input, const Factor_ *factor, const AggregateAcrossCellsBuffers< Sum_, Detected_ > &buffers, const AggregateAcrossCellsOptions &options)
Definition aggregate_across_cells.hpp:256
Aggregate single-cell expression values.
-
Options for aggregate_across_cells().
Definition aggregate_across_cells.hpp:19
+
Options for aggregate_across_cells().
Definition aggregate_across_cells.hpp:20

The array of groupings should contain integer assignments to groups 0, 1, 2, etc. For more complex groupings defined from combinations of multiple factors, the combine_factors() utility will create group assignments from unique combinations of those factors:

std::vector<int> grouping1 { 0, 0, 1, 1, 2, 2 };
std::vector<int> grouping2 { 0, 1, 0, 1, 0, 1 };
@@ -133,8 +133,8 @@

Quick start

g_opt
);
g_res.sum[0]; // vector of sums for set 1 in each cell.
-
void aggregate_across_genes(const tatami::Matrix< Data_, Index_ > &input, const std::vector< std::tuple< size_t, const Gene_ *, const Weight_ * > > &gene_sets, const AggregateAcrossGenesBuffers< Sum_ > &buffers, const AggregateAcrossGenesOptions &options)
Definition aggregate_across_genes.hpp:284
-
Options for aggregate_across_genes().
Definition aggregate_across_genes.hpp:21
+
void aggregate_across_genes(const tatami::Matrix< Data_, Index_ > &input, const std::vector< std::tuple< size_t, const Gene_ *, const Weight_ * > > &gene_sets, const AggregateAcrossGenesBuffers< Sum_ > &buffers, const AggregateAcrossGenesOptions &options)
Definition aggregate_across_genes.hpp:268
+
Options for aggregate_across_genes().
Definition aggregate_across_genes.hpp:22

Check out the reference documentation for more details.

Building projects

CMake with FetchContent

diff --git a/docs/scran__aggregate_8hpp.html b/docs/scran__aggregate_8hpp.html index 802b357..c41fffa 100644 --- a/docs/scran__aggregate_8hpp.html +++ b/docs/scran__aggregate_8hpp.html @@ -99,40 +99,43 @@
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
diff --git a/docs/scran__aggregate_8hpp__incl.map b/docs/scran__aggregate_8hpp__incl.map index 7b9209a..b6998f2 100644 --- a/docs/scran__aggregate_8hpp__incl.map +++ b/docs/scran__aggregate_8hpp__incl.map @@ -1,36 +1,39 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/docs/scran__aggregate_8hpp__incl.md5 b/docs/scran__aggregate_8hpp__incl.md5 index e207dc6..11c2abe 100644 --- a/docs/scran__aggregate_8hpp__incl.md5 +++ b/docs/scran__aggregate_8hpp__incl.md5 @@ -1 +1 @@ -057cad491b4332cd20858706b182e94c \ No newline at end of file +347a02aca69c266782aba6564ee61fdb \ No newline at end of file diff --git a/docs/scran__aggregate_8hpp__incl.png b/docs/scran__aggregate_8hpp__incl.png index 33f7c52a060e05ede92ce4046794ef3f1898c9b8..f2d1194fc86e49d052b942dc8fe7a8feac26e544 100644 GIT binary patch literal 54728 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 literal 48767 zcmag_1yq&Y7d?#9-65fLcL_*HBOo1zP&!2rkZw3qB1m_KfP|!UgVH4((%s$R-G}%0 zzvF&)-1~jQF?5LM>}Nk~uQk`)YfeMeROGNR$T8sH;II|sWi;U65G~>0;PKEXGI0N3zp|POV&UMZ;S^*fwcOM8<~`iU*C+lRUnch=$P>im_#@#-619sh zNg2E&MvC!&SB*k~B+ZC~q`n)`y7@uV!5DVD3Fa0t4ekdV-6`jBzB^#W}gjxku_d4e&wd*f&QeP}!M?V*l=(CV#x$bjAW()zD5N10T-+qXmIP zr=}{(%KkR-8{U~H7P?-GeaaKh(-lbh-xtT;Awc15CQE4W(4I}MLgFbzTpd8-o01i@vuUK|w)#v(;e-^NoBCOA@qn zbb5`h9F1;=jGUYik>U?YPwktcamDYV_-!WD3=LI6a41N5&Cx03zW{ADVfk5fC#{)aFOfjFU zZt;h9wz4J!33YXRHl0%Q?a@4XM#huvg3Oh3&+XZ2w)>m&)!njI%Zt4k{>Z`MVXM=P z!MmHO)>n{ZF(2WgH&!(brS%s5Px6&hUr9+J_}rYC9IyN?(W?p`9UT?!#u;kJm6X;xFuCYyX+LSI2nF@@$ivP<97yQBW5{m4iPb``=|%Ph^@rcc?ci_n=g-amN*Ea#E8kDBHW_k> zxE*}^_HE7IgMg3_A0O^b^?MiHnVp7>1dg}z3JQhS!ZbA5`QN|W>@EF$TVtDDQW9=G zmOl}$qoq~uvO6hUrnz`JZ)D&kBO^0XVb+}@j=P>20*dBVI&DWL4D zOgd4T4DAQ&=Jv%_Y+VehEcz4T5)vjwwIMc@ll-m@2jJX>zyc|Gfw#YY{W=;FIUM&) zzsWd!*hw+_{e}2!d#qq%SnB#Qiw7?rD|{kfHFF4*MQB*qYSZb^YGUghL#m)XN|sKU zVblG^TwG!zqMEL5Pd`_y{+RX5B8bM;TrC$k4de^T*^eb&2|EpzhYQWPJs03OC+}KH zD+11UCc;$3t^=>G+-Iw8x>d#Rf5owAGIMd2oeGDXdIz){H#>P>uO~W#?`?SfpZ)x= zsyK3DJU7yqNwCjZ;Fqu(S(+~BJ#D=S;0d6>t?$1<|A zJPu23Z@O^=+>eX}KFt1VzFbh$*MBDBx<}2=AAfaq1x{3_X1Ozjkcw(JR#i;l)vH%O zoR9(}K`r4hm;7(n``TnqfEJ zFwyv}w8rL@tSk*}TzotYEj>NG!`z43kN@s3r-WR;v%@vI?wbOb`e`#&n(qK!zVuue zVA~J=x8V6KTwI%T_N@#&JQW*95doXi&0c~K2;?Wo+?hL3IM;)}y}{T|dxnN;F15On z%uF8Gxya5w?K%E?U-8|^AFCkC zeyuxJc%Hup;e7`lnr>DN)*l?k_y#G~p72O-$gp>Ib{^#InB90c-*8S-6?ih-NoqzO z^Vo!x(A*E3FLi6}41TPV7`oF~rMpbhbaU3P5r|!{5gs&O8p3eR+L{F*Lb2PP{PS@a z(664QRL_3}P3T9iUf;Wc=<>X90BEKKyyXAuaGj5x(@ZHA)=rR-kyW|@;zgPL*9;?c zArRvF`g$!bt!IBOiHV7i=iL_hHCRF4Yx(bc1NfLo2r!71pk8t&0*wsQl{FW1$<^}z zpS=j~|DoMjT^`K;`u+R(xSPsp^{Zed0Br3NT}g1*=^}2HJyA6Lm-j_B5wn$pNj!-D zWPFy~o@ehs>F8`etA1&f*#CQ}JpkYZCOG1}y1Jy%Q4ImxX$fy{QA8B1EVJ$imk2U5 zr5EK9uvWjC1?r8cY)TR2#P(Dfm66{)f0flRigAAehf=D**T6ueo3riCmEU1{RhHO! zd3i1oAOaPR>#q|y4PKj?(t;CQjh3U#2B3DfI~9rjRDc`w9M8?~Y;&LS>EPs*l^FmM z4hi909QyrB^?NwY)OTn{2H4E&bK|TPpOZst=yMKfx!Ga!Jufy|c5U=H`y+S#aC^A> zjIS%n!T2%9x+FQ?)|lU29iQz?U`~5UuOnkVfh#xfCAhgf9JWX_K#>4^r|z)jc83Cy znT2IJJA{%JG^d#=t1-}OgK?>FBtUab67}GHDrjd8u&vs#pwt$Iv2gpd)pWeP1ewD+ zyUz?7oQ0NzYTr+MQO|uvL!0J0Yu$8v&?rHG47on6{S}7tD=<0AK)|S8tSLhm6g1pp=$FP zs;jpHIe}ES;v$C$N zgmLAAj22wX`nU{osasDIa){|Yb9w*b$AJr)kY zdzNaZn7;ELS$3nArb!-9+o&s#EIPj;9B@}jZ|}Paa3oH`uhU<@em!09#I!$G%OotE z0umcAT>y=r(ExaVMngwO|LZ#U;jiDndzXm%dAq*8J^<*Q@TV|73;N@qQiH}62LIo` ze}mivh+J)HGgrd_Lg#(EUkfN80U4Rz?lbUr{t$nVkQ#v9f+M$a`~h$uaF;6YYexaQ zzw(}*!Z4o9l;(f{`W76!LBr2U9;SWJGC)>DrKf*5EDY!A{`J^B!#hn)O>w5fs>_y+ zZtqLp)<%GYAO!dUh&u>cF4%=j!~}?<0O$Z4{^D<|-$T-;3OSxiJOXrg!^Y=`hy>6Qu~eNK|l(9jTX9G9;EV4VKDON@P9@H%W3R>f&L>cAA*Evdp0a_wbEJOXLr z0FZpN!Numaq9U1~oqn^KTuyfB7#@sDwe`k?h&-nF>;YiU9okL+xKp^^_PqN2Req5E*l5OI$$Es!old8ppU7@ad!oxKbC1AM`C|At`c(FdoM)B|)YE6AV zQgoEU<_iDg-|{f^R;UOVkd*)=9ZPRZ-IQu#w~i5(U7jyR8G3z_zgiyQ4q zX*o2;)bQOvCKQw;%6|lrE~-XG)d}?&Zd>A$L^kWpZ-%A@<3J>GrvsjA&;0%%T;>Go z-g@cv)ULEcV=~|UqP|2{tW!n>NzEaH%!;sTIqFZLoTSBlc5QFiL}iT@$O1u6~L{WplsE z`q72~sT8SRs?OK%+dSTNfa+-JY3L8QsBn(;AKB!y`r*ionM}gXtZPNwDD_QkW$NqG zIS7tmS}<@@4nFOml_7V-%>n^O{x2x^--dMDY@bQX*2^wyEQuI%!e#Kexg5v2efHjU7BCBcTxsAVn@dZBnJF2y6k{Kx&DB^%!oyDci}${6d9y)A zH?kd}iH2Q_=&o*p^wE_wX}KER)&T{*kx=@kyaoH1tCnLdh9Ke(=ryPNb0)oqb+GQh zasOin=uZEGS#4%cF9=5njmRFMm@Bx+ik?B!VGX}v?Du9mefC;A`;{%H72lDqVdY)> zwy2yRlon@A}5XiSKe_cJJhu;a2DAu_!4g>!_YW)W16nS?Ha>e5|`Amcn-?@CeEgT5(P~ctIX2<6EP*D@D->gTWg4{3w4hZ%ZZ3-~BFBaIGat`ApCg#&m0 zoDyPGyT~F>6+4PJq_klWXY?t?1gTi@bp?_$_P3(A6uwp29ca`ERl=Yh?BE2Q&jIOx&ywX7u?vk4a*8u-WqKwb)`W3U^ zoIN#5`QNIF$zuC>{(susmxz{p@GDdMq1fBVo_T0o2-nbeuLME{LROBgp;GaJdch*; zd4=J}+cTVX*mXEpl5v|5cUCSvSK;(Q(lPJH*-!q=i|-;AZ;fkNG5>aG4sKIwk%^^$ zKZ;{kWh&jMDPcz!PTziKLA2$7cCsIL1Uic_E>I1ptf0=GIIe@34a~8o+W18Im0Yo`#Z~0fil=+H#Naiy= zxHRV1uV1*uj{4l7!mEDdNhb-9@*ne%8tn1@`eE4=%RwaSdlVNZW$#m3w)7#(aCGd) z%CUAN^L@!gNuRPc2aHj*ZPo3)7? z^t%nkjiIwLq#qZY6UMff!M29LT7D0f56;8ij>LUMQ-z?_FaPxr*l@RiWlU18qnaCgR-YoP zs5qaVn1k?J&0f~=&x7ltxPPf%zp?w$wC2oM0BL1h%o^xXj1EZ~BIFbm+b`{)SLgL- zCAMTyN>8Rwg=LL3>0{Oi*@CQQg!?D!;>NDqrMSTM?bo)qvUQx1>Sv87aINsALyAu_ z$C9Ojx(iehI!|J@J~nY~+p;Gs@^j)*D+e}e3862aQ!Aw=(-*^56%u${wQ$OJz9QQH zsR^Jl3+8$NO_Voc8 z5=)W{`zm#RPN}D|EMQ!H^j>tj8T&tH5NDF;bZC#p&1(*cCPKZ z5LT_EeT*ab1GVceSViAFB5?4T;PbADPrF)VxM#>>$d-sg9=(-gGtSv2N-c(aj>p1B z(Q||L`zU=bibgq1ic!iKQ|__rWh$FO8R5NCga(|W(6|0IZEQJ8gUZp76cLu;g#oZO z?)0qcV0yXtXqy;~t8fKZ#%cbs9p`VfX=eEbRyLW}cWkqF=PF#2-^Yg8ARQoh=9c{W zo$Dd3YaUWbO6Um-V$$kB%K>TMi=ZlEF~TGWndCv5WM${JcQ#|Q#F$KvWY59RFA92k z1kS>mPSFQb(K!P#Xar8Ey#fWN&xUbkLoSeye(p>2G5&lcl-;3^tn~LgYQlFxNBQ8K z=@aG(HbXX!w_mo=wdH#BI+l%jq@<2t&+-Z+9Lm&-3(96V3P(c25$-MU7#sA%H7o>| zAS9|DAw9JrUSGl1Kir~xwRVS{ixR0K+xU|M-r%sPLco@BxyK9?3@;q6+re&GVT{Wx z8OJWedFK%g{(@tvvVnk74F`?x;_tlryCSzv*K6W8vROwzg@*;d%W@cOxho&lo&8C7&QZNibO}0KoNV^QLeo(YdgTdS}-9&#ZU?E`E5eh31!WEpI2m=gn^tD$Qe3^$o0iF$pyyBD+h*{#fN_ z!%5}FFsKdu4!cv0C<`yauOMSU+>2_)MhBu5F1HVn3?;6@Zb`mbWwOPC5L;1ZGQuqu z@h+s&R;3M@;TXMYVJtd2msBL(HNCv&+hDGHRQERif$PpYRcOBDm9zE8pjDeZH5aq< zpmIXHheGAZmrAq5gDC}sQwXdKpZ;LB@dn62sEahM(PjB6=xyX$t~c?4%J7sNIaf5# z@}mMph){$pcl7^pU3_0K%})*KJv#QsxC}c9`AgL6C_H*h-&vr;-1J0EB|V` zoa-L@D@}^M`JwW6N%SH$hED|aIYXQ&N45o!ziIId?fHE+N={FfVKWgS!#n`Y)1;+% zG@1eWtR1yQ?(=pTy_D>!X+tD-8k@x;lfzZ4;p!H)hF{i%(zo4L-z)kqq53+YPa)#M zo>k_=?j@i-GKb8Byi5t)h%)p>Pd0=(yKq9z<6k3D8rqz2e{%LA&P;s?K|N9Sw=mAttdxE) zt*xzn6Had*AA*fe#*lCTzkjKBECNkNau;w*vUL_VdeLYd-KA5fhj!+SF6|hzZU8v` z@F%+s`6vamgb{nj5?8<`h_Fz&*Tu;{9i%RJIY2OP!DnF$EDL}!os*oL2L6;>|Q2L zUDw2Qyuo$9ukPb2P=8ZGt8J#kkk#)Mp;b^7b14}nol_T#Kl2<6tT`};uzypxQ( zn4p3HVDj#3;NBmX2(|bv?zj(dtb1E&L&7PzKLIQANf9>&3|3HJ>b6-#ALzd55-TkS zNw+eFwW-7+O!Eb~>W)y4^c=EO{tn^z?AInZQHk|xbC$S?RG_%Rc~l;yZ5&PQga(21 z;kKQF>G(F>Hrub%BKA?!rSC&LdgX-A{*M>H+mr1G=}6a*Aa+~h#jj_nKq29IKmJ`hVld-nYI^{x;Le@j-71we7!gwWoT=vy zIhE{qriWL+X8L7wNsvn6pR1?&p|_NdE43*0;5GvJ*80 zatIyM>qws3&9fTL_|??~$i}fXVCb^j$Tv;nn1s^1pJPR;>R4Sl z*Nh3JgaL7y(;aN;%z@+0Pk8`Q1%Cf-7tg_1bsRVaD0t037Zq{pmP@FL9?KZCc-I3B z5^~shD7HUd7<({NC0C%5UPPO7eSO^kWGo79WB)IoAJ)12{v5XcGmMRmJqH?q4rHQG zv!JMdeH6^#)oN{La!xmgr$8_Yhd0N7$R~-4O|ErX2h^9r!NG}@6;mG|5%Kf#YFzHk zz{LFtpgS5=mS!*-JiR=vIw4x$m;2Ka?QW^)4xC8Wq zTtX(5ai`&zwF^_G;NLN}!1x_!w_0fXTkKiQoZZ+&vCeJ)uGn|0OrILxiy5mMpk=%V zA3O)5+&{fZpJBg^f#e3SOFJJBo9C>oulxJ^U4RIRv4w~$ngs-uKR}{-2NLOLd3pIz zMQ4TOAo<|Hz)x*3t|Z;u-;MCVI8%&Nomd^K26GFg^fC@`Bf?RA1vOkb-sS}H4n;3eb!;BYo2tk3QUd5W27sDXs+q4;cOt6$V{7avy7{JUNNj)hquxEVBiR-*(+aB@16WOxF z?~VdsyYsr(^JrUTQcn3MxZrMYpiap?4SroQmaNpN?vDPMnQfD`peiu8to7l>|6T{C?D6pt z`VXcGQgJiVI)iXodKdx8V^CL1Ykat6VX^(TXGru^sRbApGS`LH<22v2CA%pm{MKq^g!Pn^GbR?;$M`EOGMSOz#- z?;Kx6Qi8JlQ1@`Ni>u4|X71FjaUM0C;*K0xc21*CDMT$hV7G~+^4JQcImjW!+t$T} ziq!ddugi!*a>jqo!ns1;U=;WHM2EU|%y-nsf#uVw88D10%z;qjR8H;xbEJe5}X0zo_!L zy|_D$^jiaFn&Ru~cYkPsqVFmr)D=mk3IYU!Jlz&=Ay6G9WW~GHFLZs%1|MYC!4k>b zCI~R^)W7RtzZc7agmu7+f|FcUvxytxi+wq$GnIsn3u}=buY!$+6}Uz=tG|>%dyCjf z)>|)Jy20=#+s!mJY8~A8Fves(xViKgEi4p9ww3ZfA_WXUNMCf7rKb%M*a4RkfL11$ z%73+yYG1b+A)?#t$!}NNXt@V8LKC3mi5|5fYH4fpz8lG+%di4{N%Uqb*Bdw-nl5H- z08fj`$nc$B^aIlQ$yRRU3DBR8J8{L2rp+RGfO|t`?X%+@fO8;0YXH#|Xk8vx%OOB2 z#w~iYX;U!_Y-DH-GG&8=s-o>Z(R9}UjK7zZe9Otn$)9FpWiXw6_PS<>R+WK%_ zmdt0RGB^#~A3*iTf=TbdgwuI=IR^Z4bQzmP#ic9zwTqU0aV$UW7c(|9ydr>ss_Nrv zSLe+GFpXsZ#S-QfsIi@q0!EYL+k4>qd8QsAe!s11Zf*`x1QjOsOXI%$1sEjhOV8)P z%Jt*C`ti6=`q;K-s+fQ&O*Cg}14#ZRK*mk`*hN;S&&kP2NFbvO^BjQQ1hnsJm;Vwif7R?!J> z2OpRKZ8{4$*)p!%oT+wT(qie5ZYw9W3WETBbB=-ySmmiU*eif@_?D*Q|q8v#+*<1MM@fZwP=Tk zwUEy)-5s)TvTIm4HkF|ZMOY{KJtCmml;w(*vgB5<=G!BI=yIiqVnjL*^;kKxv_yFUZ_pkd^@C8Ezn% zFC++)WKuXIA;I+*YG7av0O8_Ei&U4d6atB<;odJ7T?h_gx5RE&o-xvrbn9?*1=!?_ zbd7w;5;BCaKtdzJ`h_HujJgp}EOKqj7FW!=BSd05!QPpG-$VXlDtWhOV$iv_$lEV` zzQ>8AGZB4j&E_e6cZ0P241eh32lvfAr>m*tnz%pDN@1}%P0T|=Q9}8SB&KbWhvd<1 zAZr4fnk;`tfvN9OVE&^^-G(h85ud0fpPI~0^&)-nc|--Wr=f%{maT&hFT2Rh0`;@u zBGzOIvR&w2 z>)S0dEl#zqNM5An1PS_`iJ^a9qEjas^UdiKrf#0khU{La`woD|yPX^+v=To_I z_(SB$1E9~$Xk`e8vT{xne7zT^Vhe+0oNq@l&+IGRgv_Q%EUl3}UnA+`Ie%sd&Tb{He#4fuuiAGfZ5>AO55f&BfZ{# zQ))F(QS@-QJGf&6J1m(~HeL8JvIR63(9XfU*6Fs|_ro(qz+?HP8CZzn{yrrwg z+35$XAiR&iAEHxEQBO@CVK;81sy*_^A!O;a+5 z;aH*%y5z@~OolipY^i&lIc*l2RF1OU&Uwz8-8Y?^hrKtSs!vwkzE(POGcj2`{PDHl z@pkF{QckVmzFkj0vp^&iF;3d*N^tdqSqGujYXp9Yv_6tPUXu64 z#z=0(4rLuEi4KZ(G3*~ot|O|s5qo;3Wb~V|N641lJQPkYg9qH}UTxUe{!CrY35Sb; zvIYqvZPd?I(reihyyP`9%Qd)rA|KyeuLu>yd*b{hhuX&f`QQ8w?#GLA(%uwBBhF_j zcg=WPdxHLb3Di}+5(9@-)EtPyMShPTxRIws?pS>Kr%k%0oY0Y<;s%>7<8#WAmU@L% zaJF6g<1$d0gmQG3W_Fi#s$0TUNN5+l%dp!MT*p>Vf>&Z5pIl!bK-SPAJ5-L=!;U@L z`bPZzsg6)$qj6kE-roKwr$!QC-@gURo1fCe`iS~m4wOe6+?s)+Z&z-eU^N<{3%Z~~ zB9DHc(tKmtig=rn8-vHP^UrD_0W+UjHZ(C~9SeqDFqnA)F7q4Rnprk@VjwSgz6uQo zN_{Xee1+ja+@VH|vhEXjmld^WL2Q$@H_OkI?E8`~OZ4}GAC=)}q66C^9}R3s5_}db znHZ(oGCXm{PScmgkd8(8VblE_yH^zY{xwlJ&e4wg6XK4>5yEu$8sBZhF z)Az+~y_*$03$+iKCaF3c2?}a6I*nNm3r^$u3!2qa9pry(eMrXXtg$Jc+l~QGEN@Ho zvZlUZma*E$BiGjy;vfq>GfRAzDG~LwDD0jY&yXVt4YEXIU+TbM{nE)#({Fe=ydduP_ ztcSIQ_;+k7E!VT%bC@#)Lac+KAHp5geCwJJdX&=mNpSz4jhrN8^gbMclEeWK*VQv} zTg5q%JeNBlMOxC3c=@)7I#KXEoBF)BPh%?ol#Ce|Ozfc=5JUJ4PngntI+1^4-tDX| z+SW_kRCx4F^Y$hU=FZxPD!Oz9Qa$n;x+ar(9?i@%1Z6@R)TA+%l#eyNbI*|?RgF;J z0H;e-?)Af?HWS?c>$gkMxAMz-RVW%4YJU&zMC?IIz@sGYyd(-~f<*t_T!X591&17N z_??1|&I9oU1L>L@m<%nFdqxDS`DkvbqirKt!BG`1VZY*WgSmU0Tclw--@qhg?BkfA zLhz&SsDh{upic}LnZb@)a}{sCVi?-={}xD;-kn~ZQ7+*x{Q+Xu)V3(2_qW?KH-yuG z4i>&x^V4N-RbY7W*6hL~E=Bgm{E48A)}%!|Xp?<|Qe98ltmKD}zvQcK_hfm$h?Vib zJC}~x6U*|;Nvc2GI`P@r4$SgCIKo+M1iDL(#|3FLC(&aw@A<%>(-FBId)ciGmsXUR zeRX?v8S&Bec`NX~0G>=D+@*T}UmeIag>64D1ifO{g}^NEC`K5j_|70G4Jszc?RwgJ zLNgA4=0}R?jPigz@Ub&(&-}WSqz&E9_d;(^ld2NXjcHg+G3RQ-A2aV33ZV0v6tG`;$>p=h|eFWyPW6X(b z42op|-J^>mq@f$+K|BZ~2&w*h*}kt0ocI`xxLg~POZ&)JMHR{ZQM@+@XJi>D0_rKb zF>q=*HP+YEKXZ&T%)0;mn*;P4ak#30jxe8zlNa7X%IEdDufI13Af=WRu!xY{5$EP||N8($QRO4B_ zne77U8>eEeF(w4rFKN?4DpB2|sfX9F<8jl6o3h#TN?n-qA5x4oB{`HUKo|0+o;Ky-<;7=vbCHtwuwnV>xHmzI3b=Nfu}j#5ui zhck_JH)Eina^b+@@?v%vh9V@@mn_yYc$=STY|vW=i#A%9<8U`_#h1Pb#g(0@w1q00 zSWJMiL%2URLh4Ybw>0bq74Tcf>LcQEgY>GMGb0?(t5W8&sbS_SH>e2FDA5;nN)DFg z8Du*1$gvq5fyshqgrm=G76_+oto1%a4l^sxrF13$Uk9h#=Xrn+v2<>bZzjMZcI;Z| zs)u=`SSyLC&&Ys@mr*NHM_};nIn!co5ibrLLn<}jNpNqMPbARpNrN_7>0ZqAJ|znw zj5G?#6-7>C?i;64ba#L3fm46bf;zC;V#|C!9;1|Z6C1k^aqAtL18Wr+Dp?cPA`;3@ zBi~hc&KURHzwABQZOc0ODPg5fX|Lj!`GcD;pX>zY!BqEo?mXu+U!lU`&OtN0f?+Y}cg%fG|8qMzADIZe0(}oF!a}&Iz>yggm4%iuEM{I(QKxigX*?~JwSQ~aPqK*-PzJ>17-tq8Y*ne-n zgcSt7#oxv<#BkmUA$I$pAmc4*|C6fV{=R8uxqS3-&i@-THzObLy=9QOmbUw1E=18A zn0SV;&(+b~rnaORX#HFKM9L@A&WdOYlQk_Rk)1?9dGv_4uZ&3swO%o(x2@HIhsFML ziLa43yUf}LgvohqV(pkXyl|J`Rdu`rEx5;GX0_LG9pI&w_t($>73L)E6juwTX>9Sr9 zi9!^6kYt+(TI4#m$)Du~MIN6}oM>ua$j}iWeB?rQS8DOj;<-qah_p~~A`(8j@dYKS zFg3OTI5p5i8lfyjYtDA0BfYrBF_0T5R@S%!EKcIqfW8r zL1W1{zd>P2jR18FEtwhUdr%?x_4*BG;RNdpFiLSQ4D*n{;HKr$dm@tF8yEt{4dPoX z|IqdGk4n)Z*BE*`=$chvDp}_6tDxis^ZHhv%HXG}Ef=y$5f1R&T%>Ce$W9*z+%^tQq5fY4(e=PkGLa=t9N5q^8B1eZP*ZsNLfm)^G6Js181 z)oa#r43oY;MCP}k-K#I9s2qMQ+V?6+?=C=R6{YTz3BpCP8&XX0dy!sT5$I@w!rwj8 ziXKmLgE_F;@1=k_0%C%S7*OolA- z$4Z63eR|HKfh41*R)L9;OwG({T>puN5TQ?&T^H_<;Y**@YLTuqBQ-U%tVEO&v*0IZ z`0Y<!KY%8kuzR&WAKlF58kF)`b%*`* zrMl~)$83kWX&5sFLGBu=YMfq*gHNp}%@Ji(-qC9fdP2;noa7})4Q41a!*9|C2~n|^7aT4FH8T2ia` zYiGMMAlbLqGgtG9w9YVSc$DIfEsBuRJ;vB!fLhSTI0qvVZg__Mq@tDIBc+Aq&2SvW z!WCMFDAW&SJkZJYQ?Vp#Q&>4(UhN>Q-?e7UauONoRg|c9cLe+@e_-G@FN?(1b29x5 z-F;8OqnG7;e1W&&RoPfy6#qWs*hI6y<9_ynrlY5UP5w;#d-g=9%Rz8X=rS_)Y8pZpTKLT6e|&p2a4BcZ`L zSjCNBA`w~cUI@s}74c%D;WIT8H1@pqv*vlmhlohEbW^#9hy}NU$aJ2BBm#BD zDK=?aYlTJIrMF=9T-JZ^DQxuLW2d~6_lHwT77Otb%<;p@cChI6FaOculNX+-yT7pa zo|RO&ew)~e_Np7pG4|5{%IILnJ$iKI;9^RXq-~{P2)D{IdEDj)^^>4h{&hU6viz5| zM_lR;9NgP7A5x?76P&k+O(g)n{6}}cA)Yw zO1tdYrDxvEz-`+qvlEfwnOv}tPH=VEZ-sja#o>KreJlMIwC?74kNFqbNBj{ZMh z06hJ)#C`jpXq*04gme}St!H&o-!6(zTs7jFcDX28ayGR%-WC!J!<8YR%6JIyyxzEe ztCNK{5J6_ngv?{b{bXI8I79VI9M8k#8b=9>CsUscwM@KROpbXW2;7oz;=UJkr%6u# z)lg+8$vHWwK}mFnK~nKhf{+n3GnWBs|7{^iC#$w;Q(Gsq>TJ%Mjh_uK8fVGrnWvIB z%HOOGD~k?NN;DIv3fFt3Wt>#mQsk}loOS8=5M;_qy>E@J=N=d~UtFcH@xIgad0E7( zn>ENcw7MV@v>znFCn{^;`EP0cFjd)9q{eXnW8~F%(m@Q*kNQ0_^q}R%)R@Bn7S@arQ|VC!=TJe0%5b z%i>wAsTa)KM*nw1&GWO`lb&)t`oD`euV0^ee=yY+li1GT7W_5P7N}C$4RZf0zg{=p z&*rTuWpy0tw1NAtG20HK3{f5H7}9ncc)Cv#e$%yJ6`r!pL_aH|4%bTZJy2He-Q5sNh0$!p0R$*55-J-T!$S~Zox?9g61^m;ZXxudMZFO{$^CN0JOVxHNu|A2xbq#Nsk(2+~4OF*~YD%2XO zGKpeIgN){q^!W^u)+Bkfn!@5s^%*%IF5u4R>OIa!r=OnMq><>qvVH=;T)8MG7@O^}Sr+Zln>XY@@?*g9+r^+?d9nq;L2dkaDaL00h4*>VJ;YZK)^wQ7b4H?!=#f1bL)ieHjalwXIA zS9-g!&o~RYYbQw(jxe=kN=UhcL?W(gXU+93$@NT1&J@Npv^DJ$Lt)k4WvzC=Qk$@m zeP^$GR%M5#$B$n(vA(C(Uxjr`8T+yh7A~=HxzE0P|AQq&x3Q)0s8T9ia0uf$K>dKz&&q#lRG2<8 z5;jA6)z+T|s>ZTcwlB_NVV!iQph)3Y$_Ry?gkw-4?hXlUKR`$nPOFpxsHue^ z{Yhh?sD?7-#Uos56gSi6KJr1^L`R&fXa##$IF3Vdl_z6y?9se-;lwEiKMs*3X%{x^6qp4{Shlbr{J-2<7oCe+|zHlKo zDmRUJj<;2nJg%Q22Maj%G`hfKG{Ml=?-JyglSCAuyhQEq!{WGJ>eYY_8z-F8I>n}J z*(K7sZJ5Nh3UGiRMv@DH0zb9#hC(rw|~hi9947L6PQhfAh#gZ zMEj^Y&75}oD^!GkjUoESa)wnJnzP+Tp^|-CC$G0|uPjv8L2jhIwcBfz2YV&f6;QMx zm2ltLULXEqPL5lwCixLzQFKy0GhhY%X>Mn{l(085mWlj^RX=Ts8gqIXZFBONV$I&K zhYyXQk|LlT!5%T}w}R40pj6@O@bp4j=gm@gaRgLFG!(rW|ZN2*J&%!YTg+uXLf%vZ2rhiHRY-fZpLN-K?3z zlg-*WXn8?ez($^l#*oWEKNj@DayjBICi5yF$((|r11~Fekk(Z-F8L5E7Ajc|%1VTy zk2Q;NNsADXtA$Y*Qv56boxbfCJ1vW^Y@GKqM-DsmvI>5kEPQB;ru(8r9WEX(ETZlk z8ELk?1>a?$_%t{m9v(${ykQXtDnni%w9smf*ZtJRf{6DgmT5bn61nFzt)N`fL&R20 z62b~GeWt$@2c=HZWmnNIj^$%~7fZwvfL&1H{+U~y)4qN{-O2;@3;WA5FQ6wSlRNA4|4xyDSmUUi)P^ElO#`zk)+`21Tc3 zOLlrSJGo=5s?W(!s~nP(7h0f;I7rxDb=X>>sMMfcq7`Sy;_paO{xYb zPNlapPnVR@pW5?b_*?v1kRM@3Ie8_SZss*~EB?`Npw0tHS9cAIE4)ABQ3f$4emOYa zd~%c+?TC*T_X?Gc{~MeklNx>HGObO+Cwjl?0ot#-7QZgancYx@tf^DD3G3x=8;{tU ztPA0OWSy$gP7R*tOZlS8t60S3`k8&CZlS?Jaft6eUubs0rnbO9{uWbbkPLnczqLE_ z&|c>gruqii!8d}@^cQ}F%^^~Xk*O8L8glPWZM^CIl5i5gcVfe7jqQG;2pxV~q}A|p zy7DP@OwXXmv97z?OIh4AqxVb-QSrp3y{1=}>=HsYJVy`QNmMf%#m2jkSESS@L}Z8cN!f{^A^TgzBN$K5jS`9!?U+&pqkDzBOVC71 zt8ckR#C!gEQiF}&y;)$dGvkT2(u%x~J{4FuR!fzG{beI2@-)gQ7Gl$F%CF12N#;YE z_>V}dn-~|ZwXU}*tkKYxn4tQT^U1my#SziSzzRaSiDSRVXppZIFH1rjf2!BeWi8)v zzR;h~jy|HgzF~IPf~wH6#p^@$3Xisfq!_ugum+-=AO63)y6w&){brhbmWT zj16L#y-ib)#@2s-Ler=)uY6MaPr@?cIC3o!pZg6DH#3fIs~{Q)?UWbCBq?rA5{N=S zHK-e1stb$nFueMuo{48B#{DrPp`?IDpf+UFjX^#wxOVEkbk#7;(bI3p6~8`PaCA@O zqR+nRP!sfN9m~?1Hm)I9#{Sk5o~l{*ISb<C+0a5+_dLO}RBcLuFC4L=Of@OpSFXT@n?>=Lr)3D!yv3u&5@`xCOC;0it{Tg(by&K%M`ESUz+h2LS#Gz6FiZ zla%ia;~gboXuql$O#n%w6mB#!ZBMQ+-qIs2I(@f&cwO#Qg)8!E{p6rx2!D7TauKm=N@CBob4ZBPpc|H2Ufa&| zcXqq9@>dlD)UIxnMF*%~D9DnD7+fxm5~|3T4ZM2i8s2l+WLL0U&_D4DQ{&0t?%=6- zFJz(hHJlqH5 zFqUsUS*T(u6P&fIP+DC1%M{TTpCGHXb|?%5@Pq zUu)e0^IPpEDkYtZ@UG!l#4msEyIuUX$ED)Deuk(q>>74i6H@h&M|e=UQ+@ij^V9iY zaE1xHZ3#UM=YNkjg%9C|99rjG>R)rd8Qw2~21F+{na0_@0ww=8w2Y?-Acl$)Hi@#f z9zItPt)f~Gr zI+#X%^0FQ8AetNSpjJTC!5FspzI-w4{j73t|mO1mVz5lf@PE;rGwC3CWn&4g<%K)#Y zdfw?e*<2kt_P(%Y?o``*HexniD`0xOzcNl7-~ZM!Nio4Ga#6T7ia|&u$0YaUWykSP zS+|RbBK;Z*R2a?QSbzVNQ$sil%Deyx3LR@8_y}dHRwYURkuD2nC@lg`0J8Bj-R0At zYFd=1xi1rbB`l#N_xi2lbvuMTJ2$ZuvOyXGLQy9SI&ZmxeOr0GbjZ1jI2qm^t=@3jB&vyh#Y;SL~ zo3=GeE^dsb3w!+{vmMJ=1+>g?dmzkP1N4meb&tl@qr-{huBf#)>D=fT*csb+^ry2!Wh4?ka;{@fCO zzJ&*K*=qnvdY_oSEXE!+22+kOm-qqQ>|X*oD5)Emt<&i?!;H*AQ4 z$y!vM_Ri$2tTC8{Ra8>?0Xw<;X~!qY#fbtXH=+CYMPG1x7d~QRi-vh)ASh)i?Re|S zn=Zh)_AIsg%{RGF0Vr*(ea3{c&pF7(hLJ+hY2|b|sAJ{Sr-6r#E)@7I)h^2gn8&al zx?w7nYs)dbriD(zS-s6qgNSnAEtTzPnm`6Hj847b{2BQ865yc1KLlN;#>B)(&vS}s zGw@?mnDN?9*cx*Exm=z9eKB#~ysLNqCJ*pI@kvR2Kpiq@_dP}pV3a@{7W`2-@ahcJ zvaQ%spu<)+&{CkvEmKc~Yx7eFjH}-Yyx3+^%@FE>;Zne-jWiS$6x4X_8Ny}iqzby~ zS`NAyh2dc#0FyCT1K;l{Q2WB+Qm$Wf!o7wG;#)tH5g`WRYohIqsOt&>r_-D-@l)>_ zJPkr%OF;dwTyL+%^IOKOI^fbPmP%p_tPOL`Zgj9DZe=|3i~@$6>0wrUTwE92c+M6s z;dQu0!EmKqccxfAG}4h4WM~QN9fSwU8KCe-s!p?BC$HfH0jT*1#+xU*Yk}BUp<9s# z3r){)y0l=rR0lEG4+HaX{5chd4M3mSb$}4t05=`WPFFYC$Ov|k=Tx!AJ$(EephWtv zbRxAM&loj$?JX=+n?DBH&ZlSJnrk{A9Zte%u3$TiC)YnoV!im8pjKM?u_CW|Z@JaG zs?l*)6{e}nfPA=d<%rid+?xAUP zIPkun4udP@AM8o&if!21GY1E*;C3ki+?YmH>+eTmfmh97?*QXRnNAr31T^h1UAhgp zry|&(ej$xm#H?GeS4wT_3lgP7+kHKqC-M=F7#$JMokSy5 zfB&{*7A-l%+nAf1U+k1sZOrVCZQyz@eES}aI1acSoaZgok65*fv$@(1Uc$1|rVwz* z*D2Nhdb~Tkx$waMKnm`8=}eiP8YJW#*hCy(bjiR^5y%OTB_qp$_xf7TBc>};5k0t~ zVa_qW?Cij-N%?QbY~DYLrNglv*?pmQo+^$*yagRC?cdE0L0)Cs5DyWQBnLQc_kkB~ z{SKz%Sl*V$YiAY-z_lxi^0o9IK{5RqcJvdkvp!)a0^U2}^8-*Luh<6z$G`{|uKF zapZfASENtrRDES@KM= z#$&i_{F^R8<6@_FU=6A_ZgF1#$#e%Bdoqqrp2Tn@^te<|D!)IRUU(`GtlN4aTVB1>XT>sN&CjtM$-A)MUE!&0Z?za6y$sFmI!rp?x zz^?;P9l{X#0$e;LdQ}e)uYpajU!jXYg_#MT+XIf4oU7xC_s%{3&(k}Vv1^StskT`; zu-t#m*S&_z>M^aO_h-h)WqrOs1O?q4yj2jX#l7~IM!{F0tgMW4i%u@a3`nYQ;Gtl! zaN8ImhZ%d#>`}_!zm23$Ee7Km5cE#S419nd6aV*j5?MlzC=-!}VEb4A(>3OvKvY=R zjq@J_Gz~HB53v#f^b|e)<^k`TCuvljQ|b@Cr;!w%P_UzT{N2(}%@Q31kg5iEp#i98Uo>eQBoJ^18GX9Ga7^ZU zIu=FDhBz&toZ(OivX3(-f&~tNVBHwY9L`rvNC5&bENWU7mPpubwSZ&`JX=KvV?^q= zBrfmuyJXzKF)=uwt`3#N&sI><`0cyFYVk8vWK#^6N?h5&ffWL15rk~zH2z57+aU;x z2)5k78gPUAEZ>UtBR(Gv5K;&!Fnh;2Y=LsgZde~d6?hf`SLEnow~Dkm>Njc{_3bMq zojKwwOd))SO>3^>*m=Yb*lU=bYxCg)2beWvrwm~awAVddZ9YdY{`8UJ<0~@~hN9m^ zb9EeEjbzHomW?I>If>AG&Q0I@!4>lv;x+hC?;w!0phmonR09_{`%NfO!+TpCZ$Qe7 zzoU7Khc7KHjQ}k|2<~QZ9vK?4=z59T2E|8;^1R7LlAftKnR{?_tr*sW;K;@dRr36cA_ z2-vP9=m-Nant)ig&2r{XAN{+xNE%#gJ-`ATY2LM; zN;-k{vIKbPc36|+9+ksYPl;{H#gC`7A~0yX;m#y)3VF#Z4(y!oeRe6|c*j?H)V+22 z-hDaXw8nK+8eEWPP$meyIG_d+BG;{l-&|3ezI##JYH*ldLwIY+$_w>$^}f;n$CEvJ) zf;C73vA)fWRz$z$=K2zVhh0{@Zm{Mi0N&i)-3{+t4=Vei)gOT8{s3UFEfhN=nIi8Y zVi{Kp6aq+as#FI%7~zJcc-9;OuEXQ^UOCOI)XJ>up%y{nJ4G z^aw&S0ypUj1~^b-Mu7Uo>>Nx$FdaWrrbzxC|Lr6^RhhZBl_lgx>z&Q@^poi9H8{fD z4_2g_)_?wYS3#g|8#CoI@2M#%(SZtw^IkWlz{i)8k?Cb{7KK{Fz`%fXj#aNxSwR5< z%x9Jp`HIS^yx~4a8$4hS1XFew@Q_<}O3S`29QJ(w$F*g8i?p6)GrBr^oLJV@bbZqr zrFkuiO~~t)en_L)4|p!ENt^yaaq_-C4}ggPB95u9=ANl~Iu0BC3|yg5 zY~Dqr0!ZD;yOgd8gGVwJ>@C@)T?%}dI*%O)lT!gAD?f> z?}lw0`%AzkgA4Qnk|qSO?U(M*4)IphjAPZgZVKPL@(VotIjA%=etrsPaL7TG4Hi)C zQte2%;u+$>&)WzyK(!a-PrOyx7xz4WG4kdVn$F-C`VcPQ)d>Ex;*@*=?Ew@m&2$i_Yp1A(s73?T@L z9|2e^R0kbzN?>jLd_D)lq*SkJjBi}D2QtDPE0=p&JeFvq=`x*8C;x92;Nf^v1}yBK zWr!#c$M-mn^!H9gL_{_OFzCFXMfV{~YHAWdK>Y#9=u`F^5S%%XD$9*q;voY|G*L1p zL_*ET=P<<#=2Jv^gL3it-U4y@Xg_GC!-jUSEuQaqdEZ3)aeWJ@gx5mosQvut$O1xL zi-fI}RW;y}5zKbbY)MrdWCpcXm^c6SgFJfTgTK8SgSxp6jLxx?BFUGUaYv^fw!<_< z%L4Wjw~HnfAsqk4T8A1{_{Bl?qWd@dRx)o-qNabd#vXToyZUiO_8C+IfP?1rZWJqe z1KZsa)Da>;vsE@D2ZI1~9~GEAfHUC(f9oq;${_$~r?l3#zW8HtkKgWHRRut*;pmI@ z`YBx458GXfzGlX@AzBoOSaS>EQ3P}3(7!`(TeiJk`rSR`am-%E=kdALMSp0+w>MV; zV~DNGN#4iDPT&9bX8L~A525b$@24K!rW_T&W@mOx!o(7(7rOQ8`aHM@E!kTYc~g3JAf{ zz$lY=n`kDCEiZehy7v@T8$?Xrz^fNfvr9w%1{D1UqA~$AJwk0Ep`dZQ|5V6OWqJw= z@!3{}$YLJ|hZsm(*KqqR1=D@Nwd(Ph=8&xjisxqy@bd=ifo|VHTRq$T{1%F_CQrok zp+++e`sazzdx#%6pg;-a5#AGW|A_&W5W@3{L(Urp=_fuTV+8(3Cge&Dk<}8i6o_19 zMy*ecFI{1Ad2oIEmx(peV%CKWORSISgTJO3B?}9S=*`s;!Y&FDINp7I=uaog-2=!O z8;;m=m2HPluCFg$0Gv>4P{+t;GqM8pn44usw9rFIdhOV%J6 z+W_Sm@a(yAcaJVzX>7%@OA6VL{@XfoQ(v)A-L~$#<87myZvT!NB~^2!W*lb}{P0 z6TZ+5`!jMH4fCu~+84z-BCC@KeBL)K6-tPu~JNStCap)v(^K3#|3-e3-ao+|UU*+}(NM zKK)wm_y8Jt0;+0%I^HMPaPze*jZ-1eAAxd0{5l1QH5Irw9(pdMT&5$i6OsyW6l8trJBjN0KkZY~aoF3krB3LsfpdZ~&p3)p~IRFlKHD zS#V||02clX$I8K9b}{11>MKdpy_g*8um z&6;?BZTIsQzdGna-u-;HZvIzeERai%;5Ft=i--^g0P_ecSm)`mK=+;RFbJe?TqNL9T&y2*)8GBIpeo@%Qh(zK>8&x>KF}7T;90H8cdI z-6lNSq?#AxY+UO-%mau?@beR0y^)0WUvp7m#SLfv@vy}ftc2#qC-?y4q6QE-h?)un zjXN}Z3YAl(t*q#wo}lOFPXzjd;KTCX%)MBV-=FW0BOwGnXd!FR0EqYkT4NHvC1_eF z%IC0k>53ue!zzak(1%B!tcYi=^+sO7fkSgs$lK=Mnjj>+Bm`wzF@dqhev%OY5|81d z^o-q5OG--M2K<52&mHPIgzksi_pcZs*VE5u$?JJ4gJc!0XAhG%R`J2=b zX$8SnK)Z8~8ze7?r#P2$+HMd;O@dnW+P=7-`!w zzr$1nw3W;S(^EmvL7`;^gNEO%OuPe;5M&3R#|B6c`);@+7?^)X7u0l_ zZ*C1)GG;SY9p=I89=0|wrq8Rq+kY|VeGotFkQo;j_vWML@adOd(ufKjeptps@4u=~ z{QAri?#Ir|M#&?bLng9);L?0Y@WJ6~bH!J1BW&G?iHRnlRR*USrc+7b#yPUkrpw2W zt$KZsF&FaweILS%H7v0fidA$RGD)Dw_(1+TYH0t{Pw}86k9nQ!HX5S!4}r6V;uzbJ z4F@if!v(0MYc3iZnonW80a4SHZ$eZsZfa$R{FW-m6UJ|ab`y>SNYK!j8^X){eugy> zzlMqs@pA#Z(9SR}@`I*<)3;_G@97$TSJ1nNUjTqkN&Cr?nAfkl%s2N091{6hR@usR z+2C^Dh4Su2jd%w%nxJrLD0|uw*hlcJVHYjrIFiJtRv+14`4_TtC2r%|Pc)d{I=ApE zxoiDgK9$!RzJHT|<_9%MXIML%uMS)4d`fZEszK;Cy?zFL(BCgdGeV@LK2qYo*4s}H zIc3%=#Cd&}3i@7XWz$1IGC;&9*q9!UN7|HGo!ie3K}Bsi-o?Zm93>-BxLx)vR8(CY zpHO7y)v7rE8gI|mkAm0GAmf3Bw*aEQ^kkI$EEc|<%z47*NwDX_5zZJbh>^N(=4iSx zyud>t?hjuWOqoL~MH@hLK(pCk>~^(9d=?^=d91+HnU%hF0X zsVPFB$~Gp+AsPUPWdQMl;+~+Bf`fy@Z_+A}^r9VR7TnjN(A3#q+~ zN{Y+j1MkL(C;{2loagS3TKGPN-rmg7F{RbNd=Y3o77zqy8x|h^=XWdVvpaxpL4l6z zp9I#>+=;5E5)L!v+eg0Wqmu`GLpM3fpB>j()ZMV0Q5$2oX}5jmxf};Zta$MW2@^I8 zHM|AYrdKgV8>ALyiR79d?x#QeJb0q7ZDgMhX&i@2yzMhQK|@pe@ndYyV83kq@{ixG zneNPt6!bAXd-Lj1?BN4$0X*DzT>h60Z#M_lznvak2D(6V`)v|gVi??+%Yr4o?xW76 zRD&0rvYkp8&j}9IcAxGf1R=iWA|tzvZ6HsMG4)U+bl18E@ok;n-#SMnoobRh% z@R^A{Q9dMrNi{xgSwM<>s2RS?Rl+S0;AS3$B)H6U49&D@TTd7lfBE%OTytT)lvD za+^|TNotjmLF*0*~U8jxk!gaw!hPLE3v23sYQ-F zFWO(~x*$)d)B5Rlr&?xlv^f!HsL;iA1j=7uP^xZz$mlh)%cS_isz+0V+f(v*{zh$l z%+#JYwe9*A)&`#ea@s+Z-9Mwa<@b^{pT>V!Q*d(tr7AX4|t1o5lJyh9ch>cGsPcK(1HXFt(RgFoU z%=%(L2BS>qFZ8k>Rm&uC4VuYKpu`9L{wF=*@~P475n1$?dl;y(%;f~uNmy)?ndK)Z z*jma_xC9KkVT`3eGZZeGx^Y7&S+5-256dP;V)4x7rJ00RRm9M;V7hQ1gi9c^G;6EO zCsBf8E9#(yE@t(Ih(cVU?SH$1(FW=C7OvSR=1FCm5uS?_mukjcyRd`?>K3==e6$Q43rb`A*M+Mk7AiagB8iU zwX)oE5u=o&HYe$c#Wfo7YmvOzN{G1+{YYHofZ*3igx&YeEZVu_mC{TfA@(;+ew4J_ zi+dpbFuO?7wlk)dz&veo@TZ$e@9FU8_egGD73;w!tZj)zEHD!GonUQe@=U9~e8<@aENo{IpLwl&Vp9Lj*!kxEm1!nEQ%WN5?4`#Zj(QXeSBpZob?G*{W=b+q zq`+Lij6`eW^KP`n0Vj<$LG~`!ktZx)2Nyb>EU=y^nFWv1CWx85o~|^KITPp6G(CJi zAI<1TUpNC7_(1Z zz^cpfrDoySo4B7zcF1w5oC)!-_ z5iP~zaJ^G4A8xQ_=FgouZDqE?Vv%tCjMxT6Vg|d&k2`A*<}29o?@gOXrJucU``9`I z*NBG4D?p!G!|Z)GonZ9U#v5OF30>GC0msA)#X4zHij}j?%K;)^I)2(q?PJWGZXvY} znUjpt4c4UQek5o7g(!ClSF!n2)w|5)#QLQ}wXm3WpXC+3_6*l4e_~Q=M-THgB*J49 z(vNEg{7Hr$;Cl%tnb7`{o-4I!G;T=zjw;5F69wz&O$cS_x79L_l8c37G(vwgIzLSW?Gg zb5bqoH25)wu2DYwADORTOAPxm#@rGt{&*(JyKURfCYSydy%AAKv}d%=jcb@(ai^ZC zyi2W&^vl3p^g#@v-V9MY;W|2E6n2^PdHZTg5^b(lLkvr3lPr0Dcgi8I>CnEFn;M?u zEIQFA0b5PJob>z0x?-{n;-)Ho&o*?kn=sxYt){ix+DI=b+W4{k<+f?mrH`4Rt(R?9 zNou|AaLb^xs+3(;-{w_=CEfhaZo!$<5&u<2WdGQ&qz1XtO5%sjB+V0^253X#aIL~C z80Xfsz3{s$^Zm}m=DN|5VGip={)Gg`o6@BnKOcOUFbQbFD;pA_%|OmliAmgM;F!%! z*l;}s9tEJ*DHCBeYV{e{2`sg5_wIP!w=U|QqL0S;)AS(7b?J7u-E5e; zvZn2yGasQEmW9VjEUYE*@VW?EaP%PE4|}=r%xqddZhp6cWM|k)F4nk>g)@ z5QcFB8R_A_ijroqM=*DHgy@F9G3C2orzsg@a*5&pro{(-6uWqcx6e_+kC?4k1JZ(o$}5B=g+aZ zUyWCQR?hoTS`~i-7sW_~WnqhM$Wl@uk=VjQTAwT-U{66Ns7f#GadS;}FRiL|WYzu8 z-Rcwc^h~PN(|UgUSK*#nrf(xXv7ALyW8eptbYX&g>GriYS&CI$cvj^mEmMVvy7+*i z7U5+4qiDC6HKqDmb78gpBn)4#lYb}~uZnTq0?do+#Oz`uhsEASYPW!3^z#E7vFo*5 zD>0H4B5ri^G^Sc&3bGdzj#1)~hjHCrZeJ!BBd6LF_lY>D3d>PXri>yBn9Wn*^zxh6 z);o|`Q39MuYAzqkJ4JbETgN@NCsR;;Y);Ov)-#^6t$Y$=>Ak|vZDcO3NgsVxQ^cxH z7)^vatNhH;Z9+SovC?Bc?H%PkgGo;Vk^_-$+zcmDLXoM#DpkUc*yzOeYps1@o#YvB_4;Nf%dPniDkQ* zBw;{+zAX1GO%TUuLh=h4#3d9Aav{0!jWkb=m!AQ7D&Hv&5lA%UHIu!otpz)G>x+MfbETZqN;%csE5~vV<7rwCf+GMOS5Xh1)tLxXg6rE9j zIp~GU75#jr5+|%9azfxggWlVwNSF~Mq^IH6TW_f6Upm^j-PzZC;+v(>l}5z!^t^OQ zlJ4QZPhZgOA{^Uv;tYk!|1Odlk9>Nrvo?BIXSk4h|7}BPxb${*0bbXN+r3rcU17v9;k_g@|f7Ckv z_M&mht`zfVa4U&=d5ya&&n=5dWUX06GYFSX}bIg3U=lsQ#eQAk95`TQQ!CrSy- zmqiCG-5jO#ufh)Et7@G$!idTeDrrSAj6-${G{O~^9z}nB+Kiic4P)YW{I|2u(zdiY z2;F1#w8_xQd4;QE+tmV(8)BPLeUo~+s2EopYvO9Z%^suQ^T}VX$|5v%y8pmsMFlP2 z?v3*LozBu~0>aStxbSJJUiK+Ds~YK*qI&)Z%)jftyN)1d-h^|0!lt)q!bRl|G{26wtR6&`?i<12?_u93yZj1*TB-C zkYtBk*^n})Amz)lk0J`CFW(e|9nHJODOlTxR_*lzrH8r6e}ui zv5c)%E-_WloNS^Z)s6 zlaY#e!&;xzUf9B@r1G+lZ}?#E?b^)Xpm|y!COi?h|BZR~bnXg9`)@(a&vuEL;bVD= zQX^?;#>OorO-A+kbpQ!tO@yMsE>UupvZVnvBMA%prtO zKTDatkR8#8!N7lQEwH501=C<*_eli>HSx_<2H=Y;{!%`dyu!Uh-G(!rCn?Yv2PRo!>rc)aagQtWl;2}9-;&;7bv4E>dqw?85C z_73JnnphQd2(&G=V^Ma#bf|HJy^)wPI(wHn+LHD!WN(+Yc@h^ymYW{jgfXEr zcEVTZyV%FMN%iud$9|`_%cB+2%MN-4ZLzZIwvM6n+QcyjIsV~C%xF0#l^0@gF?iWH zQHydJm(AXtXLqmYXt<57HaZ>g7w=x&MK~(U=U}qPle=T_WxbQ9l-{%uH`>OJ}+O-=-|y*1>9S`8JR92QMj!1 zSA1TY%<~~H9V=i=Lcae)$!WBby)wHd*_xJsl{e#^$4NG-&2lUEiYAO#?q!$m*7BQC z3~^alq<0Hykr?eJTI!7rKj|Ra+tL1%faidEh~;4J8oqSrwyC@@EBEJROg2vU3E#NP zQ9cp3h{!5JTI+O)<8}F8q7`L~UN;hcwhtc2CLOPyYQKIbDLr>e8Aqv2goK0|LjRfZ z9x8qq{cXHV^5=4teQ|2G-^e`W?uWg*jrNK>l6ollw)!_be5uCj{WA8UPgdKHmZ_%g z6W)d0QuI#t{lGMy@cjEXzmKJ@J6V3?=ak{{KcuZbHSMu5=aSe9+mc@+Ut!W{WW>a7 z)4gtY)5p>s8JKQJ5-)VS%(Tb7X^dH-8UV;}SIa#cHQ!7;r z1-Dggy4R*9ijlF2fAc3UO+L1Emip@`Vk3(&`}ne>)1(u-kAf&(n~%_q#`OKT=z0oi)3c z_amuA;$;sh<1-SYua;5J)M*u>wPR^^_Iiy(VO07`^AV}u8_MI!sU2JtG~vRJ^u@3? zbSl1@UTh>{kYjLQn@k&t9Z~Nf2sPLszShfN`c)vMPcISHSLV`(#Xnj+j8;#uYOXVM zOT5x1wNJj0mHtQ1QuF1!-Z$O!9>N9@ZrSWl%n4&zo5#6p5w^PN!@u)|lg`KktjcC% z>cTQkvPa(DNs{mxjYXz)XhAC|I%>qoBZA+HzwpH_@r{a*5i2~KedoO4W( zxSwP;|8vCc%*Zd)f-)cd7L#)oY>wIRAE2r0~!acJE&M4R5 ze4o6s-R{sTicqMIf?riia*ytuLmX;IncU(FGumpxP$o;iVOFm6q;MzIg&s-g#CC^j zvV^xkq}Pqq76@CkMM}FI!WY-1t@4-#IPGW&>)&Ec68YaTH&(75IcijCSsg-Zd6Cy= z>RhSPxW9mx9mUb{)EzTgPhK7Mf;9%k7x^+ID49d)SK@E?uGSf1PP+FF0zF;QiAFe~ zrr{d--@QiK6nY7qgYQ!1)N7hMxpDcE#})VZgyCxazgd9b6zv>$H&0HnzKA5luS`ku zQ&vLKw)nAW+{@gN9I>qhEgJX2WoZeYM_|=erf3hU%=55nIHpQtXQ#4qpr(~24d~8J z)1%JO=nFeBFXEstj%S$5Yq;CxB|8unb)idgA5cyHoF@LR1;y_) z629mNEx~=2icy@{*~Y6JBFlbIJ%V?wV=JK4t^){)u&OWp@nf2uvowEM%D%0qd-t%A4 z{CP=ct?U$Wwd34+sATo>S~Z;1@^OA)lQYYx)#rT*-A|r(SJf2qQSQdLZ#wfxpCOJA~@ zlJ72lR&ft%A+uB8>n?`l$G;5?QuY<{`m^qstSUe7KUC}ij(sSUYJ3$g&u|5)& zcEcx$RQU20V?RSg-r8mVm$mmCPEL)qNOoG8qRne(u5Mk=cgEDGj5?TV7Ac(~l4;%8 zZZy2Rg_pPOWnm6k|{5pjEG=*D4CFSYDZM~@6Y6Y42{=D10uM|FXKiHKc zZ`Efj5VEr-tLM*2%Bk13Lz!|Fs7a(XXM6X{Ywnrkf&{GwTiHPrvs%ev!P~CpHT_-Y zgakpdGOtM*Vv?T&iqXmw4@&)?3E2z&Lz>?fE_1<|<($`EDaVN8={gK=a{fq8OW?_O zVBi#?e9*`t=#!vfh(@Nm;Twi_!&!1%-4^1QHFNg`21XZF_|wvZr*-T~HeT=9mKwga z#u(-{rQwp?nl|>BPs+N#>@|WF7g69Vg60tt#VU$V%8t3zI7kSq_@0@GQ-mn2;wP-n z*4fBj@!~b#X4g(3CLP%<5FqL;>!#J6>v0QdvXK6niM+Rn@^h=2<&8czOQENfB>2LSgEt^ooX4+oIh$TICuf(+!!r@Z-Ra z{3r`z!T(Z`*{x*0nV#drO=KzxT=75JobDO}3?mOw6m&yhw`-(-g;R|@kfD5rp`~+f zdglRGY4}6z& zGvui1*npgy=0~sS%?_7jWABPf)@NI|wMpDa(akt%Rc2m2PZVFbe8gC({oyf742mgA zEQ;E|D}`M7Wo4uUd!{}7@*{Wsqymd-p~qjSX*ImDN8Vt@y>D}Ni7kHelUJ_f(0irX zoE*c=6rYl zs7*H!yN?77AJbQ&8!LmKokLh%He5M}TFs1wr2@qUr7k)l-q2iAAL6v)g?u9EPJr6+ z1m1fIuNvJa#{~sx_5AGe6%Epk<>Qo{_GZzNwXEqX4D;K=Bvc8t7Ke<peVMQpb8j{VN3!(a>|2++VM&+x3v*8<|JRw)87=!UW*gL~IRo~c~*Ml~%xal7| zE4fv|@?8>|@5#$IZ>nE-Y8NZWD_EGfw!>vuE*=1HCwmO z3TL+HL4S+KRYg9#MGJ|-MJcab*eiWiL+Q9Uv>WI5zbMT*a>CT^CN-Egl;FX-9SBa{ z99w;=DQ+Z4f*)yUkW-};coSIuZLSZ4>VwGe#Dsf0ou1vDNkz5C+ZA|G48QB;&G5Tv z^RSi^txQ7G`xr(}X{rqZUX(Lq9L>iXNSUoCU*V?Q_Gb~tVH;WV=nILEF$r;H7u0`c z9T>1CBk-i>nY6}#%2kB?-8Pb!a<~t!dH>&~+OEYDV%bVPefnRPL)yiiTv+41;h&$o zEIuU~%<5re+{0fmCoVvvQAxa0Sp6u^wNdTSZnVc}#%KC}njG?fhjHv(S4hoRx(8xe z>3w}Ch+qk(;95)@2EQoE7-U<*nrCsMP58^8BL`tn%Vp6*>qU(6gzqa}=1K37%u|Dj zp3x zFp@3ja9I*4S-ReLsup6=W$3p);0IDsDDUAb*;@-WQ*GVRj=_!_TWYMTCulI<70JXw zl0#Cd4!duYgm0sKCz)`mq0%lvQ9qxG`+gsKSB|Ty8R-{ON|^%e4@Aw?3Yd)ksWZ9- z?;ra}C2i1VNMdStEl>YU>3$Sq6<+b`UB+)EcMYr-4>5F8y)!hbPj7Zv{PL0=-+^;H zakVDr5MMthwDj*df5;WF{u(9|hgR(JZYL*Uw{6(xi|%{llQN9kd8L0z%&S;0wda}8 z)N-_=@5C)FHIDc5#Tb`zPdx0Qq+AFCBd# za<2C98nw~g$S`i<5i{mx5Sxb;ImB*|F7mWu(h~j^C*HVaUy2inoix4FSi;OrD@E}r zOksr~u?|BD!=723dAa}9lZP&g`U`Glrd`}MI|GS?`Xx{5Da$@Q?9sDJ;@!?b&cJ%b zjGRw5fc7i&-bnu1#-N$(MQ`1<6+UC@KdPQ^>e)dKr z?QAwnOXx{^Vz^2ry)ZjDCYs>jXvRV-GGEWO?#C3mMR;bgN~``j8~Gs%yJlJh#L{iX zswiIEGu+j|IkS0WPIL^z($M6TdO5p2%_ygcW6{=#T9xooS|=TI!s`PO6aTg;h88VSYleN4s8E6Hy#ZRHYgZ(t`s`61>H?+vZHwE!p2X6GOTWxq0v^Rg-l4RdT$o#`T z2=WmmmEa!ulbbhwh$v7}!jR}fys#GUSXY{?@Uh`XUa%#{TUKJ^mxbcKN|;I~ zCSiFa!#=&}#*MnJN?hm~j_HQ-(_huOXKlJk(MQ#>Wkhx%nzfz?F;)HW4x#Mr4fS< z&#?F~Xmjk(X*_2HURL&i%(v2PJ-YnJ!L}52pOH|Tc_NzH!Tr0){zS$TQH+^_GLzU z;iK2wka>9SZvykWPPs{|I`istIa2CwLIDkGp;3p@o%jYVr4`4xM_GucG zy(F-}%Cx;boW_20l$Y$5wMM?8lh}ZT4~?Q9a!Xonbi7g$8aWbHkyD>z{!dqT9aU8m zH4L0oKvG)i?vhkML_#E_OBw`GK)R#_5fPD;?vn2A77!3b8l@$qrQ_S@dEfV+@2=(Z zECunNb7uDJJ#*(bYlQl;*ZW0t3^?v7`yl&&E4(`I?THBtXoh{3Mr6|Ll^*bCN!fr&6(g^OqEu*eb zl3{uNROpx}`vWKLa?FJ4$wp_)y3;WZv8Fp^oJKX*li0%$YZV!uak6y_#-;VRZ0rx= z*b%-SBRq+Tj9fsJ)7S&f z!ZUUKTQ!60tn$T27Z2eKYgQsVOsQI|a~{%_LHyXz;(9{|DfHiCP@R7f47v}+%Dyh< zfRpF7?2wzZ#2n$TC%6*Lr0n+2V6tOX>}csRUMgw?!ro_mmzLW8$S$0{t;mOtZL4?VT!1lix?4>qljp=kh}eXZMwvctUD@DPxwlB2O||0 zZH;9?i|cLGF&Jy5%GqsX^;Z2{tOm;@I#6++jOfUm+=&%c&?eEq?e4}Yp-u`7!21TjAKTGc-xU zUGI9ArvjX5wC1t7c7t46ZRBq`?M)eCJ^7)A_Ptdh?G?;A{H6@O@v&FtLX|$CKxZX6 z|6GhmlZEskjxqMRaxj5gh{9`)=e+g=+9|LOLFT}nA%T5PDw@-$Npz`Fy&5m&ZX~9A z!VJkucUJa!b;VDb=WqWNKEiZ0_de`5|H5TSkf}(ldz)D4bK)d3O>EY(xAIR$L6(iC zF&WV}>JLae_#W}c4DFf>Dyh+*-@)q)uZZ++lX=v!lsTbFxy3wc^PWBPW>pM_DF-g5 z9V&iEm8iB{(Jiy(udW2Ht@Ug4kyK#BvzR|LfO-ot=Qs)nx$C&uJxgPSTB=d5ev0J!37H+gRsoy2Hy0m zXeik5mY-P6QY*+$*l%%BOVF3wkG-&ECnj?k!$`yx_xmT-*Q}U&&6ypy=f1i8DE42F z>na6)(|pq-?EcbDoWr~SiY19f;DJ>EUt9rsV^S+-u4Ce>yW}JN!`HEhv54roI}{j$ zFzZ5c4ML&vAR(XsWUzN%xkDjzLBFT3d;f!BVay1%vugSqY-%|D`vppl-@{QD zJC>5;BppRx)56u!zIh`108^Ev6LbHq#OFpIhMWJyqHD@MxYt^71BEFW)FiL@vTxOS zX3z0EjipX9Nt=&RIijPGXard;N-xpU2$xJiXIkVxd42dv?)s09_z~uF<^4JKl=YgN z(Lxk)>?&6MYb~{N$ zcu7A0p14{Mol@Nk);}Ui9F4Jhy4J@yMGH}b=uq&KVy%g+XUVdxb;RK+@lzOndK??{ zKqg?2#5C`6r8OsgAOtTa!boT!r#G^{xR&&8ifsg^vhJ*f(C0hca`@NK1eT8O$bXPw zdfrHZtNEEOL3h3~1fQ0Mb8GMoYlzZtk5-&4k7Ovvue*W#qYs%TJ90>I;C9_G&fgAc z(^!fwO~xh~>B`zaP}SR@AAJwInDZU-h>bIy=`?D`>ztywxlj1AlXpm`C|EmWDBo5E zG!e~OjSKdHY4`s#es8m z=bgmXF9z*lMOXc|<-{dLx`siFx$IR;Qr@=eEp5 zTHiIVWA@_Q&2N7?mv=6t@QJV{?adr@Y-mr|&-^!4ZWV9e-f?*UHFx}UP?qJ70Vxft zD}~A_`Eqh@uMA*Q1Oh2*?=|}EU#>X4(720~so8W12`n`Q_P4bI+y3f$WZ`UTEwgr* zptIaRp*R;6(p6a+vx0Gih0D3sqI@~&{ihuJN4Td`RR_gk1@`A?j%xa(k3?du9n$xr zgOxc2A6J=^L7*mS9xx{zS*X#vXfl|uzKwUC-ByOhnsJm#Y_xOD%;p`2`xx8p62kbb zzsjbyq8=RNrWC3pT_z&Kxq0JCH;i+dx|py_S+4p{J%5eXiEbW~Vwy&zD^|6CyZd`S zq`r6AVkrmhhAx3!bX`z!cP->Cq1DlLh@IFIvtYf9!4E{ea~Z;kmZ# zJowmGLUxGOuV*God0uPS4R(PMA)djg8>*_cN|gHKtE3)JZXn%KJo?5*=Sz2P%2TSV zU;46!?_!KyxPvjPq;XQ&H|-B#$tj?UIQHY$7PGTn+TztKB(FBZOt_maaqVx{S3V}% zpaIejAqO#w1l+{$^2Pro&X~8zlXl>-;$(ZJs8Cw4(fi)K&GkmY+;Cp~ z1$D(v_APFFISZb*h3`iRxk?m|QI{DtjxFR$srFK`yQq+v;JVfeoQ*~4tfm^}@?CsL zv~GwGRy{0NDl}O8MLw3`#v``;2Bo+?Mx)7A=OSn*M)%Nno z&8D%nwBXiR-Hh8cP=6^tV2@gSGZR@z5CT);dF3WzCYWxj_nBAQmr{i!af&lP zs@l0-oTwd{S-N3-W)@*hIge?YL^LTahR@$s)2pO7wWdtOOu0)_*wnd@Xw_9ltEJGp z4;$R~=ib?>^$Yb1uBEZKF*=j{DOAPol6lnC_eJBk_;7Qnv=PHiK^l6cAW0~D>^m-) ztVNWx>#3AjwZ92G49t8{PQ}@1bz3^jrU8R805eyu+A?;#cwb_A@7@FIGIh>d><8rY zYSE2blh#<|m^AE4!AG9hu!4b0QKVwW{z4^Fc@9~1x@`EeO_;z~Y46=UZ88>z=PWc$ zz=Zx(W-{Zkqu7N0gh$p1vw%WRJ&AeAS{y3nJ;`8YR&T3=h@zku21KlmK|hC`e`5Xk z+QzP^(bZdd1LnSRIhkCpe{#R`?_nrT_8|XlcrT|}rCRB+Sge}yCD&3@?st5aU)u>Ruo_4Hgpo}c7WmV=j6hUV2VjxE=kbLUjsI$EWR>?4~7vyn1B z8B2zn2Zlij5RfOr4(Ai%&M|(VeazsI=St=+S+=NkG?;ofY&4cFz&aDcEM-4SZ%CwY zcR0p9^`3U`eYTP@!;S)3dL~W=g;c_9bES75{=pi67%^GNB`N2KQj8^wAbB?Cuu`C9 z{#N5bs=ozkq*^rvOCoQ_&kPhrxo6Eo_^|^Z>{*~)wiu}8Y1|P7h1Jw6JWFCxYpR<9A7u_W**JdFLuex7~but zPcOXoBp+6_YS+syHGqF+sMViA7kAg?1#1W2dt0Aab_V%3TQ(X;15-Djc5rcUaLi2$ zyT1o!pq?Re`z)~9=h(GKH@Eo=leWdNc=!$pe`oIIt3FS&Xtj=G<*$A78rm8>DfWe) zzQQ_#r18mjY%ffnPL`*2`lQ@Z9ovRo;d?H|uRXuSHnGk4+t;u`({0CjqhWHd^crW$ zk&z>gb(JQ`P~J{YEn$4j1+o|0xNT^NcS&wezJ7ky2|oJPvEM9|cq+=9`to37yudCi zwQ)l0r1@;!VCqn#j;hSd_I#C$WO`WHZXIl5-%C394pl`2t4HuT^j8Or9psiCld-X2r67OXUy+qZ* zatDnXrI7OeFl<27er;B`(A}G@kN14dURQNpViEB3G6aHVToqemx ztGa5F-hKRN7gS}A*ZPdH)mOgga)>Q5m9Vi8>;0&+c0;N6gW3K2G5N`NG`y&$UmSRg z&$2!JKJKymXtMH-e1C4rUGHz_!cXQ~i>~4PIh{6A!A`|&L zzo&fa&cY|mCmQb~C4wF`Z@(;7%@`}DrIR;}*jkDeG3mKp_Ywt#`dC5cf#!0s)`K|8 zl(hNQKeeip5e^eWLnU)zlBraK{Xax2{BLcgAJ2vzM3F1|=!H~yI4=rHo&=p8q175+ z{u1%S^5vvv$1QZks;?C+Kvf-F?R2LF~f16D4(ZKJ`1Fd7OAcR6yTw9U4u zi}yMcFR;E^4V71w28rSjYvG|AeLbEY@LymEEKoS^PsJ*Eu}JZA}Tss^N;zDLcJ*17f5<4Dm>l;d$9)qZE3Q7s}m<|n^2=% z$}R&(UVD#v4|qxWTq8pb&G7jlFsPBlx*cfO5tHmn(4Nza;oV{E!RU0^D{(aQP|DBH zgOL|ZosH=J&rT`Z_3d~y4L*{6?h=fGW2H%dBu|tYhdvOfj{9lNhn(KSml-WKyayZO zJThNp_QKwNIgsMEZ13PC=gI1iIopTc64ZK*GZVmEKPpJdQUBwvhF=rIrus3>aX4Fp z%p}pMJPvb09^3Ej?NpFRYRbp$tTi-i?dQ=7v`O8EW&G_go)!uJ_Y#qsVxOXz#3^2R zUw~DIQ(|!QtsKiAHhkrl$zjPv@pl{C^8T5v8EOirnO~Gp*By(zoE0r(WsbX*R=uf` zFzp|wFt0q8fZ9nRkbE%NytKwG47nFcY0Yc)+g?J_aCim9^UY4fYI@ni;SR%A5gdnB zJB`U%d%WwR(jU{qlpVTV2W*g+ctE-{3BAO4GR1>2rf;P531Ziaa&We7i>9nxL!%VM zO};26k8w%-h~QX~XByB-k%}o^NGodJUJQu$c5{wUz~;W2_xM;q8rNN+NPt8WCr!9C zw=|fhPP1S>t;}@fQBe2W;R!)&DB4!p*G+%h|Mg17Jj~d9sKazGgtZ6%h_(EF&Rqm`c)QwN?4e3o5?-P z{~j65gCIt>C`~cCQsY2$oxqEVH_I6{wiRFBb0izsY26BV!m_rl8Qt-slsu~GZQBDS ze6~%UH|XSpjt7hKo!G;sQ05;nn`qb@8(BY13iaX*^1?;{Jd zxa*YC-uz!mq|pOCr6i)SNhvE89w^P@*gq=t^beNNE4+5SEB~shq?k9D#r5-n^y^W0 zZz3Q5#!XJZ%RO+y#N+$4@Wc`UQ4-GfjZK|px@*_HV%})HSq`kR<-|u;?A2rKiHtO} z^Envk9{seH0o2!Xp0kqQx|o{hb2&ZbJ)_tOIn37OuMW3FS^Cs8CYjoE*r$1d|%z1`j2nG|!vCiCq<=NraXd)1V}n4JKL zeucf&p%)aw%;AeY;js06h^qwl&3^=*YD|&r88hn{itEh9 z)S1`mS}w?(@*jKTK2WG}WQ{2@Mkq|NF{tHITni>Ox`y`k*Fuf|UJ;gCEYXWj48=NF zM5npU&}9CQiGfG=l9xx*vioh{D$MKgOtV+i5pCA#?WPY?SNzXL`W%CBTG&@U+u%lC zO*!6GWmEk%8Jsh)rRL@8NmeLebG|AE*57x$K=X@qyg+R6SD@PZ&QDrMb&LUj(kY(U zfAJ*p;uguZwYMeV3AmX0C^;|}k5_9cn$FqyorsugW0OxUu|1=9=-XrBpshIX{cj>& zc0r}0Q#KlWS-H6t&%ZN_jQ(x>6JQBGFKms^YMoyBjDR9QRdJPY8`OUCxi}@&JF|ID z3m!ohpe87YBDb_;!TVIRez#L-hhJmV{NZv5eA?<_Mhp%2Id{7TgI9ok_t*gT(xJ(h zr+L?=CMHO3<1qDX_R#t+`CgsTwp^Za!iHm0(Bh&2dT6=$`wCI+T7d7!%E}t9d1Z_+ zBf+#jz2HpL0szPV?H5@zk3p@Jv$G&_}e&kn^K3xjY$& z6@cqefa8LaW4$+F9?ow&C5Y^~_BmN52SNp~ybQ3>5GW65N0d*1oq%8_>aoWJ5BnKB z$m5ffGC*m3F8=8trVm&mgJ7~DoT$^vz&zk(TiABj5E!NV10~`mffT_H@9q5J!fBJW zrdle+e5vdFWM2>H8bI)zx95_3XkKq7R0jnIqZ885AndI&*ot=RcPDhucf)-x06S8O zz_@d%0=khESg{PCr8|3iG^$=`8M)76g4WXw?g1jn zKJh&zMyM3nqKr!;9tRcx%BRRkAVbLW;5|lE^4>$NSaAA&FMW+dzJvbZ+uE}hFt+0F zx$(fLjrcE@7iX&;g@O(Mqe7a7IJmH}T70J!J@D;YqcKEeotV%C07@QQ1ZjYObSo_J z5aj~CKzYZq6!`-)PAqRtcX}DahXHv7R|AfMVs!_U z)P1Mzx`f+;_yF8&1r?PQUf&bt-d)a%T zMUckw(@y`EcH6&o5uX*C_r%%WcGb{I5Z4yKoAy}lr?tzmPu*AItq|D{oE}VYbIbvu z(Jau$^Xu%Cfh+C=3ebA0l3h(r4gNF?e&@8eqySiLKO{n50LDSAI&c7Z^Awkb>^ytG zO!P+lA87p}fWQE#vgMivz8g@4_@E_$#>-<+?;HY;%;|W?^z`uWhU=$RPd0qGR1o+C z02#&YNP|7^NnjWc533>o0ivuxgK)n*S@i&T#^G)jaJ%{?Oyl zZN427>6ifEDwY^EJs-;_^*!#Og^Qcl5+>I{kSJyuO|27fd62d@QDzPZV?4x^x44u6 z)(Hqt6PNQ9ZVMIwVPJFN0$RA;a+Lyiyy5IacsMHy%Uif5r5^j1NUIMB2>3HrKn^~Z z1;`hE|LPD22DmM=RzFnOf9?+&*V4ojBisF3jJ%-o^uQpZ0FX!>#0htZhbQ3Rl~_;r z^S0o&g4360c$R?EEqtpDdB@v%c_ zLIWuhiJ*oMk&<=+fw=aw=r(jVGuZB)m6Njv+8bIdi^6z(dFlf&s?~u)govisX0QwgyT~J7yNo;Z5Wq{{nPhxV&j^iJ!%W z{RJh>eQ6KgmKSzyc%@qCCOa z@&*8$U5Hub5Lgg(2?c4yAZ`sIm}ILzI(U?fzNe$9;98_{cpVs zTwD0aCM$v@JN_+!3xhFn2b`z+rVTJP5Od@vF>%F&fjTx8mI)|86mQ$8-Ddv#g(zpB z;81{MG$g){iz4B9kOt-w@J9qFAd>TX0s3-$db;;R;|UQNS+^o@6NVI+r?Z@K5FFD% zef&UspT-ZU@Xj(dG-~V&fh`<>TXxcO{}Mn$3=_j~pu`{q$N{#sH%msx z%^k+Bk)sOV2^7x*xZNkK_pcN{TeBX?!iHL@d(GMC*(eyZaeSuI5mmf*KJyy0K%1JX zdN~S#4N+0tqFcf3i38jUhGEP!7@-lksk5tV+0&-?6TOIwMCgtDK0j3SKjS5-XFkn< zQUaW-3?tCYUwj(zM`mUW(EOZ6+hZAwsM`_+KaFu(Ajf2p%UQtL^UYav3+zP_wMti@pmD z&4jE69H%(=yBg3GPmi|4!@~)nt)@Xrq*vS)X4D_RQvaC><8two{zZiLKL`6Ss@JR7 z$)XSHD5W4BKms=^Q0at#M4Pn-Vnf4$(O{-whVoLnd$6jdrRDYF^)w)+J3BjnZ*26# z4MU)N#2o}PwXUtgSg_W*rx2Qn^V&!dk750Az01qHuA6bp7F>54+_qOhv})(`na*o~ zlugX*m~Xn~6)QYm=sWe{)Z*@+Aah5z@1b@ZZg6{r2)$tEq4cviLWrCFdvS3Q4`i!U z%7x43M8w{5zt!Ykzzq&1=S4`=qg{kk{l8HFNe=++>o;_p?Mil=Lq>zy zi&Y^bI8#BR_D8W{BG5#9K#?Jp1Vk~Xi!H+fTR@X$(P$tuVxpt-gOFE$HHbYbh+HRN z@LZ9H&vGGY*K@Up&b)dl!N)iJ*Bx~R5Or~2%<^8O^vF08@9>DdLnJD<;D#&cj&KUc zalR|KR%wuA+vVaS#_8s4!)LfU#AZ8^p+Ve9NHIq*j-ZQ2yh;RSbNO=i*RRyd%F2R| zC&$OC#Rg(WzZl@5k?u*zIXr_QkBNzi4~B2V1g^QY28IsQ7>&mZub%CIYSsZ#+$1D} za4}9pq$q9^&s}j&^~p$(ts6biSR#?eV$pQ{8YbrV@@I-iuLr$SUrv@Y16I!u_0}qY zZb%@}JGGv!E}GUZUD*XMc<3{pY!LkM}K>KYoe zVz`($W&ind!<*RA8$6#v@>#CwLaCHEVe_pPFe+{wgc#InV%(b)qpcifqBC#qiSDRY3F7aRFdU2+_4}?hqQ3O-$$* zB3H{sT47wL1O*X6y<9@G-O+0^6O**F?GH(z=c>c0VUaR0 z-k-pDCF-z%0mmw2-}^N%G!zau2r-qdta%yE;r(pAjA?^s3L$eq>xM0+H@B^gUEqkg zNCOQ5jUt9MM0FXEKus$0t2fPUE637vZghkPb)5kf~8hNG>`)# zLoAFJrl636-EHgwPWwgqNCJDjj#6l;#Su_nuCgK_-uxii9X9F3}zFbMI;;CXqz zdfy2MSdFIo?2zxkhpDTpPe99qgC=sINh0tzjF8}pDT3w+(*mf4FONEjpIESaL^7K zbl@P7X9&svE~H}hO;p~+Rn6LT4KKt^5(3F%IuPi8Ln6P${S8ujLP|;nFoz*p zm_y?fKmPp&frCM`j)rXg5}wcE>Z&~4Ob^JoAp1n{dE^`5h=@|(D<7oBgy;Vd#vaGN zykcVUX=!v&HzNnnAakFH{~RVV*ZX~C;SrPxaRSe9Knu=-gdcL06;2WszyRT)1f*=3TYS{Q22m~jEss}`|*Vs#z-VoH6Dy8>N#=? z^cL6}L1hgrF$EZZfYY_DIXkY6FuT$3H+J7qj)Dfo518Sc@0GWk^r2C zg&YORVnCYDgoH>&UVa~rxmfiqtVGCAxK3FZc(8GBG9Y|Aum1=E%dsKmxV5k8H3Hj% zWjX}Kwt|8}I<$K#ICKO?#eL{7dkBl^vaX5PaNxL|bkJVff7`v2!VIPAR+dX*BPG;7 zh~F1GWDVg6%2FC68-$VsG)Q73O+#i}kgOJZSvX?05BXk3LDe^sDNo==V|@71K68Ae zJBN-966+09m_kFQ7@)xT0KVuRaQ8^%Ip=+32stm30)me$r6mRl3uI2N!S~6nir-to zWUP;j)+(G~m2aJZjA<|qk3j0nMOzMB8uUpyF#cxK&5-gP%zGqPgab)bQYHW5iy?V4 zBpKNt#BLGHKv9%uP*;Ah2Z^&bbB*!P2B@LLfhgVsa%u7VJ3~b+Q1}wV^a$Kf1O-_}D}qg0NsF`HOYyF0A@o)p3qJ63 z2t%>97c<9z{~s>gZI?aVk zfp+yqQaOV=(j`Uc!N5>DW}90`~$wS*Q4xo7#K zsn2B#H7~|E5K~Z9l@Qu-IusmsPep)g1omGH4$OgzUxo@Dd4}+_?3(^*<93+9*Xn5c zdEuSHa#pgWw`cmyc=2aA+(0|Oei?cWJslmL@ztX9T_o3l)v-)Sa6s}05?=)}`^idc zVhEURJw3tD>eMsk@Q`tfyJkij&eMRb-0|Kxl-8SbO^FaNAb>1x`9f=f!lv811er@y zP7rjMu7N;Ig?}A#FAL<0w$neU^*!NHKt?{>BXES2bdX=lf#W@UVd>kv(gi?mvLpOf z1dv<_e&Z`uED%1Gr>kDdL$a}daUZ-|3+PUIDe{yS2I#)NR|Svbp?)t1mKtUlX2g;y zEt;>zpVj@W8X$l(a+V;>?q_6VwC`O!5oUf1vx>?GM@PO$Up>*j!THUpV$(cH)FA+w zH-K=`dXp9oI;uT8Ifsb``=wqYWDX484RYEPv{xo(X2fGfFxw+HG1gT95t#05g^5_g zh@UX!Bbz^A;V)|06*d4{SJX&gl6?qSeVAjY*msfW*;7=oAJ}{7>3J9K#3D@6r9ne8 zfF^)QuTYr4{7fs_?VczSou0y4`22cy;%$ck8@m)(iLQWuwC4A(f9lcH73%Rpn;RRi z$KEF>@0wknpLjvNP)7p&3ztvI8O$?k<=fM-3umr24q^6&wqKIq6MhJ# zM1dE^>*MfA(T`V?{>Hsx`-VKve;xe^CO3@+_dlq(|LN&c8i`b2PxYX;ZJSjd8CgGxoC{xcU&q@ToH4dkZ;p@8 zjwVyM;KTjS{+uiOhmGMGr`wfah0k>LpXdfGYV^Nb-t1kE*&`^wDVX&QZk&EP=$_p4 mnYnoV1QmII|KIEP&1RG_!Tvv;DuP+amlR}GWQwIt0{$PLc|0os diff --git a/docs/scran__aggregate_8hpp_source.html b/docs/scran__aggregate_8hpp_source.html index edbabd5..cefa12f 100644 --- a/docs/scran__aggregate_8hpp_source.html +++ b/docs/scran__aggregate_8hpp_source.html @@ -105,7 +105,7 @@
Aggregate expression values across genes.
Clean up a categorical factor.
Combine categorical factors into a single factor.
-
Aggregate single-cell expression values.
Definition aggregate_across_cells.hpp:14
+
Aggregate single-cell expression values.
Definition aggregate_across_cells.hpp:15