omp_loop.h
Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033 #ifndef _GLIBCXX_PARALLEL_OMP_LOOP_H
00034 #define _GLIBCXX_PARALLEL_OMP_LOOP_H 1
00035
00036 #include <omp.h>
00037
00038 #include <parallel/settings.h>
00039 #include <parallel/basic_iterator.h>
00040 #include <parallel/base.h>
00041
00042 namespace __gnu_parallel
00043 {
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061 template<typename RandomAccessIterator,
00062 typename Op,
00063 typename Fu,
00064 typename Red,
00065 typename Result>
00066 Op
00067 for_each_template_random_access_omp_loop(RandomAccessIterator begin,
00068 RandomAccessIterator end,
00069 Op o, Fu& f, Red r, Result base,
00070 Result& output,
00071 typename std::iterator_traits
00072 <RandomAccessIterator>::
00073 difference_type bound)
00074 {
00075 typedef typename
00076 std::iterator_traits<RandomAccessIterator>::difference_type
00077 difference_type;
00078
00079 difference_type length = end - begin;
00080 thread_index_t num_threads =
00081 __gnu_parallel::min<difference_type>(get_max_threads(), length);
00082
00083 Result *thread_results;
00084
00085 # pragma omp parallel num_threads(num_threads)
00086 {
00087 # pragma omp single
00088 {
00089 num_threads = omp_get_num_threads();
00090 thread_results = new Result[num_threads];
00091
00092 for (thread_index_t i = 0; i < num_threads; ++i)
00093 thread_results[i] = Result();
00094 }
00095
00096 thread_index_t iam = omp_get_thread_num();
00097
00098 # pragma omp for schedule(dynamic, _Settings::get().workstealing_chunk_size)
00099 for (difference_type pos = 0; pos < length; ++pos)
00100 thread_results[iam] =
00101 r(thread_results[iam], f(o, begin+pos));
00102 }
00103
00104 for (thread_index_t i = 0; i < num_threads; ++i)
00105 output = r(output, thread_results[i]);
00106
00107 delete [] thread_results;
00108
00109
00110
00111 f.finish_iterator = begin + length;
00112
00113 return o;
00114 }
00115
00116 }
00117
00118 #endif