36 if (
static_cast<typename std::make_unsigned<NumWorkers_>::type
>(num_workers) > std::numeric_limits<typename Output::size_type>::max()) {
129#ifdef SUBPAR_CUSTOM_PARALLELIZE_RANGE
130 if constexpr(nothrow_) {
131#ifdef SUBPAR_CUSTOM_PARALLELIZE_RANGE_NOTHROW
132 SUBPAR_CUSTOM_PARALLELIZE_RANGE_NOTHROW(num_workers, num_tasks, run_task_range);
134 SUBPAR_CUSTOM_PARALLELIZE_RANGE(num_workers, num_tasks, run_task_range);
137 SUBPAR_CUSTOM_PARALLELIZE_RANGE(num_workers, num_tasks, run_task_range);
141 if (num_tasks == 0) {
145 if (num_workers <= 1 || num_tasks == 1) {
146 run_task_range(0, 0, num_tasks);
151 Task_ tasks_per_worker;
153 if (internal::ge(num_workers, num_tasks)) {
154 num_workers = num_tasks;
155 tasks_per_worker = 1;
158 tasks_per_worker = num_tasks / num_workers;
159 remainder = num_tasks % num_workers;
162 auto errors = internal::create_error_vector<nothrow_>(num_workers);
164#if defined(_OPENMP) && !defined(SUBPAR_NO_OPENMP_RANGE) && !defined(SUBPAR_NO_OPENMP)
165#define SUBPAR_USES_OPENMP 1
166#define SUBPAR_USES_OPENMP_RANGE 1
170 #pragma omp parallel for num_threads(num_workers)
171 for (
int w = 0; w < num_workers; ++w) {
172 Task_ start = w * tasks_per_worker + (w < remainder ? w : remainder);
173 Task_ length = tasks_per_worker + (w < remainder);
175 if constexpr(nothrow_) {
176 run_task_range(w, start, length);
179 run_task_range(w, start, length);
181 errors[w] = std::current_exception();
188#undef SUBPAR_USES_OPENMP
189#undef SUBPAR_USES_OPENMP_RANGE
192 std::vector<std::thread> workers;
193 workers.reserve(num_workers);
195 for (
int w = 0; w < num_workers; ++w) {
196 Task_ length = tasks_per_worker + (w < remainder);
198 if constexpr(nothrow_) {
199 workers.emplace_back(run_task_range, w, start, length);
201 workers.emplace_back([&run_task_range,&errors](
int w, Task_ start, Task_ length) ->
void {
203 run_task_range(w, start, length);
205 errors[w] = std::current_exception();
207 }, w, start, length);
213 for (
auto& wrk : workers) {
218 if constexpr(!nothrow_) {
219 for (
const auto& e : errors) {
221 std::rethrow_exception(e);
void parallelize_range(int num_workers, Task_ num_tasks, Run_ run_task_range)
Parallelize a range of tasks across multiple workers.
Definition range.hpp:128