17template <
typename I,
typename CM,
typename F>
20 tbb::parallel_for( tbb::blocked_range(
begin,
end ),
21 [&] (
const tbb::blocked_range<I>& range )
24 for (
I i = range.begin(); i < range.end(); ++i )
29template <
typename I,
typename CM,
typename F>
41 auto callingThreadId = std::this_thread::get_id();
42 std::atomic<bool> keepGoing{
true };
46 constexpr int hardware_destructive_interference_size = 64;
47 struct alignas(hardware_destructive_interference_size) S
49 std::atomic<size_t> processed{ 0 };
51 static_assert(
alignof(S) == hardware_destructive_interference_size );
52 static_assert(
sizeof(S) == hardware_destructive_interference_size );
54 tbb::parallel_for( tbb::blocked_range(
begin,
end ),
55 [&] (
const tbb::blocked_range<I>& range )
57 const bool report = std::this_thread::get_id() == callingThreadId;
58 size_t myProcessed = 0;
60 for (
I i = range.begin(); i < range.end(); ++i )
62 if ( !keepGoing.load( std::memory_order_relaxed ) )
65 if ( ( ++myProcessed % reportProgressEvery ) == 0 )
69 if ( !cb(
float( myProcessed + s.processed.load( std::memory_order_relaxed ) ) /
size ) )
70 keepGoing.store(
false, std::memory_order_relaxed );
74 s.processed.fetch_add( myProcessed, std::memory_order_relaxed );
79 const auto total = s.processed.fetch_add( myProcessed, std::memory_order_relaxed );
80 if ( report && !cb(
float( total ) /
size ) )
81 keepGoing.store(
false, std::memory_order_relaxed );
83 return keepGoing.load( std::memory_order_relaxed );
94template <
typename I,
typename ...F>
104template <
typename I,
typename L,
typename ...F>
113template <
typename T,
typename ...F>
116 return ParallelFor(
size_t(0), v.size(), std::forward<F>( f )... );
122template <
typename T,
typename I,
typename ...F>
131std::pair<T, T>
parallelMinMax(
const std::vector<T>& vec,
const T * topExcluding =
nullptr )
133 auto minmax = tbb::parallel_reduce( tbb::blocked_range<size_t>( 0, vec.size() ), MinMax<T>{},
134 [&] (
const tbb::blocked_range<size_t> range, MinMax<T> curMinMax )
136 for ( size_t i = range.begin(); i < range.end(); i++ )
139 if ( topExcluding && std::abs( val ) >= *topExcluding )
141 if ( val < curMinMax.min )
143 if ( val > curMinMax.max )
148 [&] (
const MinMax<T>& a,
const MinMax<T>& b )
170 return { minmax.min, minmax.max };
175template<
typename T,
typename I>
180 T min = std::numeric_limits<T>::max();
181 T max = std::numeric_limits<T>::lowest();
185 return tbb::parallel_reduce( tbb::blocked_range<I>(
I(0), vec.
endId() ), MinMaxArg{},
186 [&] (
const tbb::blocked_range<I> range, MinMaxArg curr )
188 for ( I i = range.begin(); i < range.end(); i++ )
191 if ( topExcluding && std::abs( val ) >= *topExcluding )
193 if ( val < curr.min )
198 if ( val > curr.max )
206 [&] ( MinMaxArg a,
const MinMaxArg& b )
std::vector<T>-like container that requires specific indexing type,
Definition MRMesh/MRVector.h:20
I beginId() const
returns the identifier of the first element
Definition MRMesh/MRVector.h:123
I endId() const
returns backId() + 1
Definition MRMesh/MRVector.h:127
auto begin(const BitSet &a)
Definition MRMesh/MRBitSet.h:280
auto end(const BitSet &)
Definition MRMesh/MRBitSet.h:282
auto parallelMinMaxArg(const Vector< T, I > &vec, const T *topExcluding=nullptr)
Definition MRParallelFor.h:176
auto ParallelFor(I begin, I end, F &&... f)
Definition MRParallelFor.h:95
std::pair< T, T > parallelMinMax(const std::vector< T > &vec, const T *topExcluding=nullptr)
Definition MRParallelFor.h:131
std::function< bool(float)> ProgressCallback
Definition MRMesh/MRMeshFwd.h:576
void For(I begin, I end, const CM &callMaker, F &&f)
Definition MRParallelFor.h:18
Definition MRCameraOrientationPlugin.h:8
ImVec2 size(const ViewportRectangle &rect)
Definition MRViewport.h:32
I
Definition MRMesh/MRMeshFwd.h:88
Definition MRParallel.h:18
Definition MRParallel.h:32