diff --git a/uppsrc/Core/Algo.h b/uppsrc/Core/Algo.h index 60e8363dc..4f9645b0d 100644 --- a/uppsrc/Core/Algo.h +++ b/uppsrc/Core/Algo.h @@ -61,7 +61,7 @@ int Count(const Range& r, const V& val) } template -int CountIf(const Range& r, Predicate p) +int CountIf(const Range& r, const Predicate& p) { int count = 0; for(const auto& x : r) diff --git a/uppsrc/Core/CoAlgo.h b/uppsrc/Core/CoAlgo.h index b3ad14728..34d6f25de 100644 --- a/uppsrc/Core/CoAlgo.h +++ b/uppsrc/Core/CoAlgo.h @@ -33,7 +33,8 @@ void CoPartition(Range& r, const Lambda& lambda) while(begin < end) { auto e = begin + min(chunk, size_t(end - begin)); co & [=] { - lambda(SubRange(begin, e)); + auto sr = SubRange(begin, e); // we need l-value + lambda(sr); }; begin = e; } @@ -49,7 +50,8 @@ void CoPartition(const Range& r, const Lambda& lambda, int max_chunk = INT_MAX) while(begin < end) { auto e = begin + min(chunk, size_t(end - begin)); co & [=] { - lambda(SubRange(begin, e)); + auto sr = SubRange(begin, e); // we need l-value + lambda(sr); }; begin = e; } @@ -94,6 +96,30 @@ ValueTypeOf CoSum(const T& c) return CoSum(c, (ValueTypeOf)0); } +template +int CoCount(const Range& r, const V& val) +{ + int count = 0; + CoPartition(r, [=, &val, &count](const SubRangeOf& r) { + int n = Count(r, val); + CoWork::FinLock(); + count += n; + }); + return count; +} + +template +int CoCountIf(const Range& r, const Predicate& p) +{ + int count = 0; + CoPartition(r, [=, &p, &count](const SubRangeOf& r) { + int n = CountIf(r, p); + CoWork::FinLock(); + count += n; + }); + return count; +} + template int CoFindBest(const Range& r, const Better& better) { diff --git a/uppsrc/Core/src.tpp/CoAlgo$en-us.tpp b/uppsrc/Core/src.tpp/CoAlgo$en-us.tpp index a7253c431..ffa422cb7 100644 --- a/uppsrc/Core/src.tpp/CoAlgo$en-us.tpp +++ b/uppsrc/Core/src.tpp/CoAlgo$en-us.tpp @@ -52,6 +52,21 @@ alueTypeOf]<[*@4 T]>_[* CoSum]([@(0.0.255) const]_[*@4 T][@(0.0.255) `&]_[*@3 c] [s2;%% Same as CoSum(c, 0).&] [s3;%% &] [s4; &] +[s5;:Upp`:`:CoCount`(const Range`&`,const V`&`): [@(0.0.255) template]_<[@(0.0.255) class +]_[*@4 Range], [@(0.0.255) class]_[*@4 V]>_[@(0.0.255) int]_[* CoCount]([@(0.0.255) const]_[*@4 R +ange][@(0.0.255) `&]_[*@3 r], [@(0.0.255) const]_[*@4 V][@(0.0.255) `&]_[*@3 val])&] +[s2;%% Counts the number of elements in the Range [%-*@3 r] that are +equal to [%-*@3 val]. Runs in parallel.&] +[s3;%% &] +[s4; &] +[s5;:Upp`:`:CoCountIf`(const Range`&`,const Predicate`&`): [@(0.0.255) template]_<[@(0.0.255) c +lass]_[*@4 Range], [@(0.0.255) class]_[*@4 Predicate]>_[@(0.0.255) int]_[* CoCountIf]([@(0.0.255) c +onst]_[*@4 Range][@(0.0.255) `&]_[*@3 r], [@(0.0.255) const]_[*@4 Predicate][@(0.0.255) `&]_[*@3 p +])&] +[s2; [%% Counts the number of elements in the Range ][*@3 r][%% that satisfy +condition ][*@3 p][%% . ]Runs in parallel, [*@3 p ]must be reentrant.&] +[s3;%% &] +[s4; &] [s5;:Upp`:`:CoFindBest`(const Range`&`,const Better`&`): [@(0.0.255) template]_<[@(0.0.255) c lass]_[*@4 Range], [@(0.0.255) class]_[*@4 Better]>_[@(0.0.255) int]_[* CoFindBest]([@(0.0.255) c onst]_[*@4 Range][@(0.0.255) `&]_[*@3 r], [@(0.0.255) const]_[*@4 Better][@(0.0.255) `&]_[*@3 b diff --git a/uppsrc/Core/src.tpp/algo$en-us.tpp b/uppsrc/Core/src.tpp/algo$en-us.tpp index cb62aaea8..04679bd12 100644 --- a/uppsrc/Core/src.tpp/algo$en-us.tpp +++ b/uppsrc/Core/src.tpp/algo$en-us.tpp @@ -69,9 +69,10 @@ ge][@(0.0.255) `&]_[*@3 r], [@(0.0.255) const]_[*@4 V][@(0.0.255) `&]_[*@3 val]) equal to [%-*@3 val] .&] [s3;%% &] [s4; &] -[s5;:Upp`:`:CountIf`(const Range`&`,Predicate`): [@(0.0.255) template]_<[@(0.0.255) class -]_[*@4 Range], [@(0.0.255) class]_[*@4 Predicate]>_[@(0.0.255) int]_[* CountIf]([@(0.0.255) c -onst]_[*@4 Range][@(0.0.255) `&]_[*@3 r], [*@4 Predicate]_[*@3 p])&] +[s5;:Upp`:`:CountIf`(const Range`&`,const Predicate`&`): [@(0.0.255) template]_<[@(0.0.255) c +lass]_[*@4 Range], [@(0.0.255) class]_[*@4 Predicate]>_[@(0.0.255) int]_[* CountIf]([@(0.0.255) c +onst]_[*@4 Range][@(0.0.255) `&]_[*@3 r], [@(0.0.255) const]_[*@4 Predicate][@(0.0.255) `&]_[*@3 p +])&] [s2;%% Counts the number of elements in the Range [%-*@3 r] that satisfy condition [%-*@3 p].&] [s3;%% &]