diff options
author | Anton Samokhvalov <pg83@yandex.ru> | 2022-02-10 16:45:17 +0300 |
---|---|---|
committer | Daniil Cherednik <dcherednik@yandex-team.ru> | 2022-02-10 16:45:17 +0300 |
commit | d3a398281c6fd1d3672036cb2d63f842d2cb28c5 (patch) | |
tree | dd4bd3ca0f36b817e96812825ffaf10d645803f2 /util/generic | |
parent | 72cb13b4aff9bc9cf22e49251bc8fd143f82538f (diff) | |
download | ydb-d3a398281c6fd1d3672036cb2d63f842d2cb28c5.tar.gz |
Restoring authorship annotation for Anton Samokhvalov <pg83@yandex.ru>. Commit 2 of 2.
Diffstat (limited to 'util/generic')
168 files changed, 9860 insertions, 9860 deletions
diff --git a/util/generic/adaptor.h b/util/generic/adaptor.h index ea9aba9331..b88a65fc81 100644 --- a/util/generic/adaptor.h +++ b/util/generic/adaptor.h @@ -4,13 +4,13 @@ #include "typetraits.h" namespace NPrivate { - template <class Range> + template <class Range> class TReverseRangeStorage { public: - TReverseRangeStorage(Range&& range) - : Base_(std::forward<Range>(range)) - { - } + TReverseRangeStorage(Range&& range) + : Base_(std::forward<Range>(range)) + { + } decltype(auto) Base() const { return *Base_.Ptr(); @@ -37,9 +37,9 @@ namespace NPrivate { template <class Range, bool hasReverseIterators = HasReverseIterators<Range>((i32)0, nullptr)> class TReverseRangeBase: public TReverseRangeStorage<Range> { using TBase = TReverseRangeStorage<Range>; - + public: - using TBase::Base; + using TBase::Base; using TBase::TBase; auto begin() const { @@ -62,9 +62,9 @@ namespace NPrivate { template <class Range> class TReverseRangeBase<Range, false>: public TReverseRangeStorage<Range> { using TBase = TReverseRangeStorage<Range>; - + public: - using TBase::Base; + using TBase::Base; using TBase::TBase; auto begin() const { @@ -89,11 +89,11 @@ namespace NPrivate { }; template <class Range> - class TReverseRange: public TReverseRangeBase<Range> { + class TReverseRange: public TReverseRangeBase<Range> { using TBase = TReverseRangeBase<Range>; - + public: - using TBase::Base; + using TBase::Base; using TBase::TBase; TReverseRange(TReverseRange&&) = default; diff --git a/util/generic/adaptor_ut.cpp b/util/generic/adaptor_ut.cpp index 37b6776ffc..721f849f93 100644 --- a/util/generic/adaptor_ut.cpp +++ b/util/generic/adaptor_ut.cpp @@ -3,10 +3,10 @@ #include <library/cpp/testing/unittest/registar.h> -struct TOnCopy: yexception { +struct TOnCopy: yexception { }; -struct TOnMove: yexception { +struct TOnMove: yexception { }; struct TState { diff --git a/util/generic/algorithm.cpp b/util/generic/algorithm.cpp index 699dbda235..d89586737e 100644 --- a/util/generic/algorithm.cpp +++ b/util/generic/algorithm.cpp @@ -1 +1 @@ -#include "algorithm.h" +#include "algorithm.h" diff --git a/util/generic/algorithm.h b/util/generic/algorithm.h index b6d759535e..badfb88993 100644 --- a/util/generic/algorithm.h +++ b/util/generic/algorithm.h @@ -1,16 +1,16 @@ #pragma once - + #include "is_in.h" #include "utility.h" - + #include <util/system/defaults.h> #include <util/generic/fwd.h> -#include <numeric> -#include <algorithm> -#include <iterator> +#include <numeric> +#include <algorithm> +#include <iterator> #include <utility> - + namespace NPrivate { template <class I, class F, class P> I ExtremeElementBy(I begin, I end, F func, P pred) { @@ -33,16 +33,16 @@ namespace NPrivate { } } -template <class T> +template <class T> static inline void Sort(T f, T l) { - std::sort(f, l); -} - -template <class T, class C> + std::sort(f, l); +} + +template <class T, class C> static inline void Sort(T f, T l, C c) { - std::sort(f, l, c); -} - + std::sort(f, l, c); +} + template <class TContainer> static inline void Sort(TContainer& container) { Sort(container.begin(), container.end()); @@ -65,14 +65,14 @@ static inline void SortBy(TContainer& container, const TGetKey& getKey) { template <class T> static inline void StableSort(T f, T l) { - std::stable_sort(f, l); -} - -template <class T, class C> + std::stable_sort(f, l); +} + +template <class T, class C> static inline void StableSort(T f, T l, C c) { - std::stable_sort(f, l, c); -} - + std::stable_sort(f, l, c); +} + template <class TContainer> static inline void StableSort(TContainer& container) { StableSort(container.begin(), container.end()); @@ -94,30 +94,30 @@ static inline void StableSortBy(TContainer& container, const TGetKey& getKey) { } template <class T> -static inline void PartialSort(T f, T m, T l) { - std::partial_sort(f, m, l); -} - -template <class T, class C> -static inline void PartialSort(T f, T m, T l, C c) { - std::partial_sort(f, m, l, c); -} - +static inline void PartialSort(T f, T m, T l) { + std::partial_sort(f, m, l); +} + +template <class T, class C> +static inline void PartialSort(T f, T m, T l, C c) { + std::partial_sort(f, m, l, c); +} + template <class T, class R> static inline R PartialSortCopy(T f, T l, R of, R ol) { - return std::partial_sort_copy(f, l, of, ol); + return std::partial_sort_copy(f, l, of, ol); } template <class T, class R, class C> static inline R PartialSortCopy(T f, T l, R of, R ol, C c) { - return std::partial_sort_copy(f, l, of, ol, c); + return std::partial_sort_copy(f, l, of, ol, c); +} + +template <class I, class T> +static inline I Find(I f, I l, const T& v) { + return std::find(f, l, v); } -template <class I, class T> -static inline I Find(I f, I l, const T& v) { - return std::find(f, l, v); -} - template <class C, class T> static inline auto Find(C&& c, const T& v) { using std::begin; @@ -140,11 +140,11 @@ static inline auto FindPtr(C&& c, const T& v) { return FindPtr(begin(c), end(c), v); } -template <class I, class P> -static inline I FindIf(I f, I l, P p) { - return std::find_if(f, l, p); -} - +template <class I, class P> +static inline I FindIf(I f, I l, P p) { + return std::find_if(f, l, p); +} + template <class C, class P> static inline auto FindIf(C&& c, P p) { using std::begin; @@ -153,24 +153,24 @@ static inline auto FindIf(C&& c, P p) { return FindIf(begin(c), end(c), p); } -template <class I, class P> +template <class I, class P> static inline bool AllOf(I f, I l, P pred) { return std::all_of(f, l, pred); } -template <class C, class P> +template <class C, class P> static inline bool AllOf(const C& c, P pred) { using std::begin; using std::end; return AllOf(begin(c), end(c), pred); } -template <class I, class P> +template <class I, class P> static inline bool AnyOf(I f, I l, P pred) { return std::any_of(f, l, pred); } -template <class C, class P> +template <class C, class P> static inline bool AnyOf(const C& c, P pred) { using std::begin; using std::end; @@ -178,13 +178,13 @@ static inline bool AnyOf(const C& c, P pred) { } // FindIfPtr - return NULL if not found. Works for arrays, containers, iterators -template <class I, class P> -static inline auto FindIfPtr(I f, I l, P pred) -> decltype(&*f) { +template <class I, class P> +static inline auto FindIfPtr(I f, I l, P pred) -> decltype(&*f) { I found = FindIf(f, l, pred); return (found != l) ? &*found : nullptr; } -template <class C, class P> +template <class C, class P> static inline auto FindIfPtr(C&& c, P pred) { using std::begin; using std::end; @@ -208,13 +208,13 @@ static inline size_t FindIndexIf(C&& c, P p) { } //EqualToOneOf(x, "apple", "orange") means (x == "apple" || x == "orange") -template <typename T> -inline bool EqualToOneOf(const T&) { +template <typename T> +inline bool EqualToOneOf(const T&) { return false; } - -template <typename T, typename U, typename... Other> -inline bool EqualToOneOf(const T& x, const U& y, const Other&... other) { + +template <typename T, typename U, typename... Other> +inline bool EqualToOneOf(const T& x, const U& y, const Other&... other) { return x == y || EqualToOneOf(x, other...); } @@ -228,86 +228,86 @@ static inline size_t CountOf(const T& x, const U& y, const Other&... other) { return static_cast<size_t>(x == y) + CountOf(x, other...); } -template <class I> -static inline void PushHeap(I f, I l) { - std::push_heap(f, l); -} - -template <class I, class C> -static inline void PushHeap(I f, I l, C c) { - std::push_heap(f, l, c); -} - -template <class I> -static inline void PopHeap(I f, I l) { - std::pop_heap(f, l); -} - -template <class I, class C> -static inline void PopHeap(I f, I l, C c) { - std::pop_heap(f, l, c); -} - -template <class I> -static inline void MakeHeap(I f, I l) { - std::make_heap(f, l); -} - -template <class I, class C> -static inline void MakeHeap(I f, I l, C c) { - std::make_heap(f, l, c); -} - +template <class I> +static inline void PushHeap(I f, I l) { + std::push_heap(f, l); +} + +template <class I, class C> +static inline void PushHeap(I f, I l, C c) { + std::push_heap(f, l, c); +} + +template <class I> +static inline void PopHeap(I f, I l) { + std::pop_heap(f, l); +} + +template <class I, class C> +static inline void PopHeap(I f, I l, C c) { + std::pop_heap(f, l, c); +} + +template <class I> +static inline void MakeHeap(I f, I l) { + std::make_heap(f, l); +} + +template <class I, class C> +static inline void MakeHeap(I f, I l, C c) { + std::make_heap(f, l, c); +} + template <class I> static inline void SortHeap(I f, I l) { - std::sort_heap(f, l); + std::sort_heap(f, l); } template <class I, class C> static inline void SortHeap(I f, I l, C c) { - std::sort_heap(f, l, c); -} - -template <class I, class T> -static inline I LowerBound(I f, I l, const T& v) { - return std::lower_bound(f, l, v); -} - -template <class I, class T, class C> -static inline I LowerBound(I f, I l, const T& v, C c) { - return std::lower_bound(f, l, v, c); -} - + std::sort_heap(f, l, c); +} + +template <class I, class T> +static inline I LowerBound(I f, I l, const T& v) { + return std::lower_bound(f, l, v); +} + +template <class I, class T, class C> +static inline I LowerBound(I f, I l, const T& v, C c) { + return std::lower_bound(f, l, v, c); +} + template <class I, class T, class TGetKey> static inline I LowerBoundBy(I f, I l, const T& v, const TGetKey& getKey) { return std::lower_bound(f, l, v, [&](auto&& left, auto&& right) { return getKey(left) < right; }); } -template <class I, class T> -static inline I UpperBound(I f, I l, const T& v) { - return std::upper_bound(f, l, v); -} - -template <class I, class T, class C> -static inline I UpperBound(I f, I l, const T& v, C c) { - return std::upper_bound(f, l, v, c); -} - +template <class I, class T> +static inline I UpperBound(I f, I l, const T& v) { + return std::upper_bound(f, l, v); +} + +template <class I, class T, class C> +static inline I UpperBound(I f, I l, const T& v, C c) { + return std::upper_bound(f, l, v, c); +} + template <class I, class T, class TGetKey> static inline I UpperBoundBy(I f, I l, const T& v, const TGetKey& getKey) { return std::upper_bound(f, l, v, [&](auto&& left, auto&& right) { return left < getKey(right); }); } -template <class T> -static inline T Unique(T f, T l) { - return std::unique(f, l); -} - -template <class T, class P> -static inline T Unique(T f, T l, P p) { - return std::unique(f, l, p); -} - +template <class T> +static inline T Unique(T f, T l) { + return std::unique(f, l); +} + +template <class T, class P> +static inline T Unique(T f, T l, P p) { + return std::unique(f, l, p); +} + template <class T, class TGetKey> static inline T UniqueBy(T f, T l, const TGetKey& getKey) { return Unique(f, l, [&](auto&& left, auto&& right) { return getKey(left) == getKey(right); }); @@ -344,7 +344,7 @@ void Erase(C& c, const TValue& value) { template <class C, class P> void EraseIf(C& c, P p) { - c.erase(std::remove_if(c.begin(), c.end(), p), c.end()); + c.erase(std::remove_if(c.begin(), c.end(), p), c.end()); } template <class C, class P> @@ -360,82 +360,82 @@ void EraseNodesIf(C& c, P p) { template <class T1, class T2> static inline bool Equal(T1 f1, T1 l1, T2 f2) { - return std::equal(f1, l1, f2); + return std::equal(f1, l1, f2); } template <class T1, class T2, class P> static inline bool Equal(T1 f1, T1 l1, T2 f2, P p) { - return std::equal(f1, l1, f2, p); + return std::equal(f1, l1, f2, p); } template <class TI, class TO> static inline TO Copy(TI f, TI l, TO t) { - return std::copy(f, l, t); + return std::copy(f, l, t); } template <class TI, class TO> static inline TO UniqueCopy(TI f, TI l, TO t) { - return std::unique_copy(f, l, t); + return std::unique_copy(f, l, t); } template <class TI, class TO, class TP> static inline TO UniqueCopy(TI f, TI l, TO t, TP p) { - return std::unique_copy(f, l, t, p); + return std::unique_copy(f, l, t, p); } template <class TI, class TO, class TP> static inline TO RemoveCopyIf(TI f, TI l, TO t, TP p) { - return std::remove_copy_if(f, l, t, p); + return std::remove_copy_if(f, l, t, p); } template <class TI, class TO> static inline TO ReverseCopy(TI f, TI l, TO t) { - return std::reverse_copy(f, l, t); + return std::reverse_copy(f, l, t); } template <class TI1, class TI2, class TO> static inline TO SetUnion(TI1 f1, TI1 l1, TI2 f2, TI2 l2, TO p) { - return std::set_union(f1, l1, f2, l2, p); + return std::set_union(f1, l1, f2, l2, p); } template <class TI1, class TI2, class TO, class TC> static inline TO SetUnion(TI1 f1, TI1 l1, TI2 f2, TI2 l2, TO p, TC c) { - return std::set_union(f1, l1, f2, l2, p, c); + return std::set_union(f1, l1, f2, l2, p, c); } template <class TI1, class TI2, class TO> static inline TO SetDifference(TI1 f1, TI1 l1, TI2 f2, TI2 l2, TO p) { - return std::set_difference(f1, l1, f2, l2, p); + return std::set_difference(f1, l1, f2, l2, p); } template <class TI1, class TI2, class TO, class TC> static inline TO SetDifference(TI1 f1, TI1 l1, TI2 f2, TI2 l2, TO p, TC c) { - return std::set_difference(f1, l1, f2, l2, p, c); + return std::set_difference(f1, l1, f2, l2, p, c); } template <class TI1, class TI2, class TO> static inline TO SetSymmetricDifference(TI1 f1, TI1 l1, TI2 f2, TI2 l2, TO p) { - return std::set_symmetric_difference(f1, l1, f2, l2, p); + return std::set_symmetric_difference(f1, l1, f2, l2, p); } template <class TI1, class TI2, class TO, class TC> static inline TO SetSymmetricDifference(TI1 f1, TI1 l1, TI2 f2, TI2 l2, TO p, TC c) { - return std::set_symmetric_difference(f1, l1, f2, l2, p, c); + return std::set_symmetric_difference(f1, l1, f2, l2, p, c); } template <class TI1, class TI2, class TO> static inline TO SetIntersection(TI1 f1, TI1 l1, TI2 f2, TI2 l2, TO p) { - return std::set_intersection(f1, l1, f2, l2, p); + return std::set_intersection(f1, l1, f2, l2, p); } template <class TI1, class TI2, class TO, class TC> static inline TO SetIntersection(TI1 f1, TI1 l1, TI2 f2, TI2 l2, TO p, TC c) { - return std::set_intersection(f1, l1, f2, l2, p, c); + return std::set_intersection(f1, l1, f2, l2, p, c); } template <class I, class T> static inline void Fill(I f, I l, const T& v) { - std::fill(f, l, v); + std::fill(f, l, v); } template <typename I, typename S, typename T> @@ -443,23 +443,23 @@ static inline I FillN(I f, S n, const T& v) { return std::fill_n(f, n, v); } -template <class T> -static inline void Reverse(T f, T l) { - std::reverse(f, l); +template <class T> +static inline void Reverse(T f, T l) { + std::reverse(f, l); } -template <class T> -static inline void Rotate(T f, T m, T l) { - std::rotate(f, m, l); +template <class T> +static inline void Rotate(T f, T m, T l) { + std::rotate(f, m, l); } -template <typename It, typename Val> +template <typename It, typename Val> Val Accumulate(It begin, It end, Val val) { // std::move since C++20 return std::accumulate(begin, end, std::move(val)); } -template <typename It, typename Val, typename BinOp> +template <typename It, typename Val, typename BinOp> Val Accumulate(It begin, It end, Val val, BinOp binOp) { // std::move since C++20 return std::accumulate(begin, end, std::move(val), binOp); @@ -482,39 +482,39 @@ static inline Val InnerProduct(It1 begin1, It1 end1, It2 begin2, Val val) { return std::inner_product(begin1, end1, begin2, val); } -template <typename It1, typename It2, typename Val, typename BinOp1, typename BinOp2> +template <typename It1, typename It2, typename Val, typename BinOp1, typename BinOp2> static inline Val InnerProduct(It1 begin1, It1 end1, It2 begin2, Val val, BinOp1 binOp1, BinOp2 binOp2) { - return std::inner_product(begin1, end1, begin2, val, binOp1, binOp2); + return std::inner_product(begin1, end1, begin2, val, binOp1, binOp2); } template <typename TVectorType> static inline typename TVectorType::value_type InnerProduct(const TVectorType& lhs, const TVectorType& rhs, typename TVectorType::value_type val = typename TVectorType::value_type()) { - return std::inner_product(lhs.begin(), lhs.end(), rhs.begin(), val); + return std::inner_product(lhs.begin(), lhs.end(), rhs.begin(), val); } template <typename TVectorType, typename BinOp1, typename BinOp2> static inline typename TVectorType::value_type InnerProduct(const TVectorType& lhs, const TVectorType& rhs, typename TVectorType::value_type val, BinOp1 binOp1, BinOp2 binOp2) { - return std::inner_product(lhs.begin(), lhs.end(), rhs.begin(), val, binOp1, binOp2); + return std::inner_product(lhs.begin(), lhs.end(), rhs.begin(), val, binOp1, binOp2); } -template <class T> +template <class T> static inline T MinElement(T begin, T end) { - return std::min_element(begin, end); + return std::min_element(begin, end); } -template <class T, class C> +template <class T, class C> static inline T MinElement(T begin, T end, C comp) { - return std::min_element(begin, end, comp); + return std::min_element(begin, end, comp); } -template <class T> +template <class T> static inline T MaxElement(T begin, T end) { - return std::max_element(begin, end); + return std::max_element(begin, end); } -template <class T, class C> +template <class T, class C> static inline T MaxElement(T begin, T end, C comp) { - return std::max_element(begin, end, comp); + return std::max_element(begin, end, comp); } template <class I, class F> @@ -551,13 +551,13 @@ auto MinElementBy(const C& c, F&& func) { template <class TOp, class... TArgs> void ApplyToMany(TOp op, TArgs&&... args) { - int dummy[] = {((void)op(std::forward<TArgs>(args)), 0)...}; + int dummy[] = {((void)op(std::forward<TArgs>(args)), 0)...}; Y_UNUSED(dummy); } -template <class TI, class TOp> +template <class TI, class TOp> inline void ForEach(TI f, TI l, TOp op) { - std::for_each(f, l, op); + std::for_each(f, l, op); } namespace NPrivate { @@ -601,18 +601,18 @@ namespace NPrivate { template <class T, class TOp> constexpr ::TEnableIfTuple<T, bool> AllOf(T&& t, TOp&& op) { return ::NPrivate::AllOfImpl( - std::forward<T>(t), - std::forward<TOp>(op), - std::make_index_sequence<std::tuple_size<std::decay_t<T>>::value>{}); + std::forward<T>(t), + std::forward<TOp>(op), + std::make_index_sequence<std::tuple_size<std::decay_t<T>>::value>{}); } // check that TOp return true for at least one element from tuple T template <class T, class TOp> constexpr ::TEnableIfTuple<T, bool> AnyOf(T&& t, TOp&& op) { return ::NPrivate::AnyOfImpl( - std::forward<T>(t), - std::forward<TOp>(op), - std::make_index_sequence<std::tuple_size<std::decay_t<T>>::value>{}); + std::forward<T>(t), + std::forward<TOp>(op), + std::make_index_sequence<std::tuple_size<std::decay_t<T>>::value>{}); } template <class T, class TOp> @@ -623,19 +623,19 @@ constexpr ::TEnableIfTuple<T> ForEach(T&& t, TOp&& op) { std::make_index_sequence<std::tuple_size<std::decay_t<T>>::value>{}); } -template <class T1, class T2, class O> +template <class T1, class T2, class O> static inline void Transform(T1 b, T1 e, T2 o, O f) { - std::transform(b, e, o, f); + std::transform(b, e, o, f); } -template <class T1, class T2, class T3, class O> +template <class T1, class T2, class T3, class O> static inline void Transform(T1 b1, T1 e1, T2 b2, T3 o, O f) { - std::transform(b1, e1, b2, o, f); + std::transform(b1, e1, b2, o, f); } template <class T, class V> -inline typename std::iterator_traits<T>::difference_type Count(T first, T last, const V& value) { - return std::count(first, last, value); +inline typename std::iterator_traits<T>::difference_type Count(T first, T last, const V& value) { + return std::count(first, last, value); } template <class TContainer, class TValue> @@ -645,38 +645,38 @@ static inline auto Count(const TContainer& container, const TValue& value) { template <class It, class P> static inline auto CountIf(It first, It last, P p) { - return std::count_if(first, last, p); + return std::count_if(first, last, p); } -template <class C, class P> +template <class C, class P> static inline auto CountIf(const C& c, P pred) { using std::begin; using std::end; return CountIf(begin(c), end(c), pred); } -template <class I1, class I2> +template <class I1, class I2> static inline std::pair<I1, I2> Mismatch(I1 b1, I1 e1, I2 b2) { - return std::mismatch(b1, e1, b2); + return std::mismatch(b1, e1, b2); } -template <class I1, class I2, class P> +template <class I1, class I2, class P> static inline std::pair<I1, I2> Mismatch(I1 b1, I1 e1, I2 b2, P p) { - return std::mismatch(b1, e1, b2, p); + return std::mismatch(b1, e1, b2, p); } template <class RandomIterator> static inline void NthElement(RandomIterator begin, RandomIterator nth, RandomIterator end) { - std::nth_element(begin, nth, end); + std::nth_element(begin, nth, end); } template <class RandomIterator, class Compare> static inline void NthElement(RandomIterator begin, RandomIterator nth, RandomIterator end, Compare compare) { - std::nth_element(begin, nth, end, compare); + std::nth_element(begin, nth, end, compare); } // no standard implementation until C++14 -template <class I1, class I2> +template <class I1, class I2> static inline std::pair<I1, I2> Mismatch(I1 b1, I1 e1, I2 b2, I2 e2) { while (b1 != e1 && b2 != e2 && *b1 == *b2) { ++b1; @@ -685,7 +685,7 @@ static inline std::pair<I1, I2> Mismatch(I1 b1, I1 e1, I2 b2, I2 e2) { return std::make_pair(b1, b2); } -template <class I1, class I2, class P> +template <class I1, class I2, class P> static inline std::pair<I1, I2> Mismatch(I1 b1, I1 e1, I2 b2, I2 e2, P p) { while (b1 != e1 && b2 != e2 && p(*b1, *b2)) { ++b1; @@ -696,32 +696,32 @@ static inline std::pair<I1, I2> Mismatch(I1 b1, I1 e1, I2 b2, I2 e2, P p) { template <class It, class Val> static inline bool BinarySearch(It begin, It end, const Val& val) { - return std::binary_search(begin, end, val); + return std::binary_search(begin, end, val); } template <class It, class Val, class Comp> static inline bool BinarySearch(It begin, It end, const Val& val, Comp comp) { - return std::binary_search(begin, end, val, comp); + return std::binary_search(begin, end, val, comp); } template <class It, class Val> static inline std::pair<It, It> EqualRange(It begin, It end, const Val& val) { - return std::equal_range(begin, end, val); + return std::equal_range(begin, end, val); } template <class It, class Val, class Comp> static inline std::pair<It, It> EqualRange(It begin, It end, const Val& val, Comp comp) { - return std::equal_range(begin, end, val, comp); + return std::equal_range(begin, end, val, comp); } template <class ForwardIt> bool IsSorted(ForwardIt begin, ForwardIt end) { - return std::is_sorted(begin, end); + return std::is_sorted(begin, end); } template <class ForwardIt, class Compare> bool IsSorted(ForwardIt begin, ForwardIt end, Compare comp) { - return std::is_sorted(begin, end, comp); + return std::is_sorted(begin, end, comp); } template <class TIterator, typename TGetKey> @@ -731,7 +731,7 @@ bool IsSortedBy(TIterator begin, TIterator end, const TGetKey& getKey) { template <class It, class Val> void Iota(It begin, It end, Val val) { - std::iota(begin, end, val); + std::iota(begin, end, val); } template <class TI, class TO, class S> diff --git a/util/generic/algorithm_ut.cpp b/util/generic/algorithm_ut.cpp index e2c8278448..8d732fcc0c 100644 --- a/util/generic/algorithm_ut.cpp +++ b/util/generic/algorithm_ut.cpp @@ -1,7 +1,7 @@ #include <library/cpp/testing/unittest/registar.h> -#include "algorithm.h" -#include "strbuf.h" +#include "algorithm.h" +#include "strbuf.h" #include "string.h" static auto isOne = [](char c) { return c == '1'; }; @@ -56,16 +56,16 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { UNIT_ASSERT(3 == Count(array, '1')); } - struct TStrokaNoCopy: TString { - public: - TStrokaNoCopy(const char* p) + struct TStrokaNoCopy: TString { + public: + TStrokaNoCopy(const char* p) : TString(p) - { - } - - private: - TStrokaNoCopy(const TStrokaNoCopy&); - void operator=(const TStrokaNoCopy&); + { + } + + private: + TStrokaNoCopy(const TStrokaNoCopy&); + void operator=(const TStrokaNoCopy&); }; Y_UNIT_TEST(CountOfTest) { @@ -88,7 +88,7 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { UNIT_ASSERT_VALUES_EQUAL(CountOf(TString("xyz"), TStringBuf("123"), TStringBuf("poi")), 0); UNIT_ASSERT_VALUES_EQUAL(CountOf(TString("xyz"), TStringBuf("123"), TStringBuf("poi"), TStringBuf("xyz")), - 1); + 1); // TStringBuf and const char * UNIT_ASSERT_VALUES_EQUAL(CountOf(TStringBuf("xyz"), "123", "poi"), 0); @@ -98,7 +98,7 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { UNIT_ASSERT_VALUES_EQUAL(CountOf(TStringBuf("xyz"), TString("123"), TString("poi")), 0); UNIT_ASSERT_VALUES_EQUAL(CountOf(TStringBuf("xyz"), TString("123"), TString("poi"), TString("xyz")), - 1); + 1); } Y_UNIT_TEST(EqualToOneOfTest) { @@ -113,9 +113,9 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { TStrokaNoCopy x("x"); TStrokaNoCopy y("y"); TStrokaNoCopy z("z"); - const char* px = "x"; - const char* py = "y"; - const char* pz = "z"; + const char* px = "x"; + const char* py = "y"; + const char* pz = "z"; UNIT_ASSERT(1 == EqualToOneOf(x, px, py)); UNIT_ASSERT(1 == EqualToOneOf(y, px, py)); @@ -149,10 +149,10 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { } } - struct TVectorNoCopy: std::vector<int> { + struct TVectorNoCopy: std::vector<int> { public: TVectorNoCopy() = default; - + private: TVectorNoCopy(const TVectorNoCopy&); void operator=(const TVectorNoCopy&); @@ -164,8 +164,8 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { v.push_back(2); v.push_back(3); - int array[3] = {1, 2, 3}; - const int array_const[3] = {1, 2, 3}; + int array[3] = {1, 2, 3}; + const int array_const[3] = {1, 2, 3}; //test (const, non-const) * (iterator, vector, array) * (found, not found) variants. // value '3' is in container, value '4' is not @@ -186,20 +186,20 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { v.push_back(2); v.push_back(3); - int array[3] = {1, 2, 3}; - const int array_const[3] = {1, 2, 3}; + int array[3] = {1, 2, 3}; + const int array_const[3] = {1, 2, 3}; //test (const, non-const) * (iterator, vector, array) * (found, not found) variants. // search, that 2*2 == 4, but there is no value 'x' in array that (x*x == 3) for (int j = 3; j <= 4; ++j) { - TestFindIfPtrFoundValue<int*>(j, FindIfPtr(v, [j](int i) { return i * i == j; })); - TestFindIfPtrFoundValue<int*>(j, FindIfPtr(v.begin(), v.end(), [j](int i) { return i * i == j; })); - const TVectorNoCopy& q = v; - TestFindIfPtrFoundValue<const int*>(j, FindIfPtr(q, [j](int i) { return i * i == j; })); - - TestFindIfPtrFoundValue<const int*>(j, FindIfPtr(q.begin(), q.end(), [j](int i) { return i * i == j; })); - TestFindIfPtrFoundValue<int*>(j, FindIfPtr(array, [j](int i) { return i * i == j; })); - TestFindIfPtrFoundValue<const int*>(j, FindIfPtr(array_const, [j](int i) { return i * i == j; })); + TestFindIfPtrFoundValue<int*>(j, FindIfPtr(v, [j](int i) { return i * i == j; })); + TestFindIfPtrFoundValue<int*>(j, FindIfPtr(v.begin(), v.end(), [j](int i) { return i * i == j; })); + const TVectorNoCopy& q = v; + TestFindIfPtrFoundValue<const int*>(j, FindIfPtr(q, [j](int i) { return i * i == j; })); + + TestFindIfPtrFoundValue<const int*>(j, FindIfPtr(q.begin(), q.end(), [j](int i) { return i * i == j; })); + TestFindIfPtrFoundValue<int*>(j, FindIfPtr(array, [j](int i) { return i * i == j; })); + TestFindIfPtrFoundValue<const int*>(j, FindIfPtr(array_const, [j](int i) { return i * i == j; })); } } @@ -214,7 +214,7 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { UNIT_ASSERT_EQUAL(2, FindIndex(v, 3)); UNIT_ASSERT_EQUAL(NPOS, FindIndex(v, 42)); - int array[3] = {1, 2, 3}; + int array[3] = {1, 2, 3}; UNIT_ASSERT_EQUAL(0, FindIndex(array, 1)); UNIT_ASSERT_EQUAL(1, FindIndex(array, 2)); @@ -323,12 +323,12 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { int data[] = {3, 2, 1, 4, 6, 5, 7, 9, 8}; TVector<int> testVector(data, data + Y_ARRAY_SIZE(data)); - size_t medianInd = testVector.size() / 2; + size_t medianInd = testVector.size() / 2; NthElement(testVector.begin(), testVector.begin() + medianInd, testVector.end()); UNIT_ASSERT_EQUAL(testVector[medianInd], 5); - NthElement(testVector.begin(), testVector.begin() + medianInd, testVector.end(), [](int lhs, int rhs) { return lhs > rhs; }); + NthElement(testVector.begin(), testVector.begin() + medianInd, testVector.end(), [](int lhs, int rhs) { return lhs > rhs; }); UNIT_ASSERT_EQUAL(testVector[medianInd], 5); } @@ -336,12 +336,12 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { const char* data[] = {"3", "234", "1231", "333", "545345", "11", "111", "55", "66"}; TVector<TString> testVector(data, data + Y_ARRAY_SIZE(data)); - size_t medianInd = testVector.size() / 2; + size_t medianInd = testVector.size() / 2; NthElement(testVector.begin(), testVector.begin() + medianInd, testVector.end()); auto median = testVector.begin() + medianInd; - for (auto it0 = testVector.begin(); it0 != median; ++it0) { - for (auto it1 = median; it1 != testVector.end(); ++it1) { + for (auto it0 = testVector.begin(); it0 != median; ++it0) { + for (auto it1 = median; it1 != testVector.end(); ++it1) { UNIT_ASSERT(*it0 <= *it1); } } @@ -368,13 +368,13 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { { TVector<size_t> data = {10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0}; - bool test = BinarySearch(data.begin(), data.end(), (size_t)9, TGreater<size_t>()); + bool test = BinarySearch(data.begin(), data.end(), (size_t)9, TGreater<size_t>()); UNIT_ASSERT_EQUAL(test, true); - test = BinarySearch(data.begin(), data.end(), (size_t)11, TGreater<size_t>()); + test = BinarySearch(data.begin(), data.end(), (size_t)11, TGreater<size_t>()); UNIT_ASSERT_EQUAL(test, false); - test = BinarySearch(data.rbegin(), data.rend(), (size_t)1); + test = BinarySearch(data.rbegin(), data.rend(), (size_t)1); UNIT_ASSERT_EQUAL(test, true); } } @@ -409,7 +409,7 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { UNIT_ASSERT_EQUAL(tmp.second - tmp.first, 3); using PairOfVectorReverse = std::pair<TVector<size_t>::reverse_iterator, TVector<size_t>::reverse_iterator>; - PairOfVectorReverse tmpR = EqualRange(data.rbegin(), data.rend(), (size_t)0); + PairOfVectorReverse tmpR = EqualRange(data.rbegin(), data.rend(), (size_t)0); UNIT_ASSERT_EQUAL(tmpR.first, data.rbegin()); UNIT_ASSERT_EQUAL(tmpR.second - tmpR.first, 2); @@ -503,7 +503,7 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { Y_UNIT_TEST(SortByTest) { TVector<int> collection = {10, 2, 7}; - SortBy(collection, [](int x) { return -x; }); + SortBy(collection, [](int x) { return -x; }); TVector<int> expected = {10, 7, 2}; UNIT_ASSERT_VALUES_EQUAL(collection, expected); } @@ -544,7 +544,7 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { } Y_UNIT_TEST(CopyNTest) { - int data[] = {1, 2, 3, 4, 8, 7, 6, 5}; + int data[] = {1, 2, 3, 4, 8, 7, 6, 5}; const size_t vSize = 10; TVector<int> result(10, 0); size_t toCopy = 5; @@ -616,12 +616,12 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { const int array[] = {1, 2, 5, 3, 4, 5}; UNIT_ASSERT_VALUES_EQUAL(*MaxElementBy(array, [](int x) { return x * x; - }), 5); + }), 5); const TVector<int> vec(array, array + Y_ARRAY_SIZE(array)); UNIT_ASSERT_VALUES_EQUAL(*MaxElementBy(vec, [](int x) { return -1.0 * x; - }), 1); + }), 1); int arrayMutable[] = {1, 2, 5, 3, 4, 5}; auto maxPtr = MaxElementBy(arrayMutable, [](int x) { return x; }); @@ -642,12 +642,12 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { const int array[] = {2, 3, 4, 1, 5}; UNIT_ASSERT_VALUES_EQUAL(*MinElementBy(array, [](int x) -> char { return 'a' + x; - }), 1); + }), 1); const TVector<int> vec(std::begin(array), std::end(array)); UNIT_ASSERT_VALUES_EQUAL(*MinElementBy(vec, [](int x) { return -x; - }), 5); + }), 5); int arrayMutable[] = {1, 2, 5, 3, 4, 5}; auto minPtr = MinElementBy(arrayMutable, [](int x) { return x; }); @@ -702,20 +702,20 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { UNIT_ASSERT_EQUAL(res, 15); struct TVisitor { - TVisitor(int& acc) - : Acc(acc) - { - } - void operator()(const TString& s) { - Acc += s.size(); - }; - void operator()(int v) { - Acc += v * 2; - }; + TVisitor(int& acc) + : Acc(acc) + { + } + void operator()(const TString& s) { + Acc += s.size(); + }; + void operator()(int v) { + Acc += v * 2; + }; int& Acc; }; - TString s{"8-800-555-35-35"}; - ApplyToMany(TVisitor{res = 0}, 1, s, 5, s); + TString s{"8-800-555-35-35"}; + ApplyToMany(TVisitor{res = 0}, 1, s, 5, s); UNIT_ASSERT_EQUAL(res, 12 + 2 * static_cast<int>(s.size())); } @@ -740,7 +740,7 @@ Y_UNIT_TEST_SUITE(TAlgorithm) { auto pred = [](auto s) { return s.size() == 3; }; UNIT_ASSERT_VALUES_EQUAL(AllOf(ts, pred), AllOf(ts, pred)); } - } + } Y_UNIT_TEST(TestTupleAnyOf) { UNIT_ASSERT(!AnyOf(std::tuple<>{}, [](auto) { return true; })); diff --git a/util/generic/array_ref.cpp b/util/generic/array_ref.cpp index cca3998cd9..e5b6a3c1a6 100644 --- a/util/generic/array_ref.cpp +++ b/util/generic/array_ref.cpp @@ -1 +1 @@ -#include "array_ref.h" +#include "array_ref.h" diff --git a/util/generic/array_ref.h b/util/generic/array_ref.h index 741982a0b1..1ac60ac7d3 100644 --- a/util/generic/array_ref.h +++ b/util/generic/array_ref.h @@ -1,7 +1,7 @@ -#pragma once - +#pragma once + #include <util/generic/yexception.h> - + #include <algorithm> #include <initializer_list> #include <iterator> @@ -40,19 +40,19 @@ public: , S_(0) { } - + constexpr inline TArrayRef(T* data, size_t len) noexcept : T_(data) , S_(len) { } - + constexpr inline TArrayRef(T* begin, T* end) noexcept : T_(begin) , S_(end - begin) { } - + constexpr inline TArrayRef(std::initializer_list<T> list) noexcept : T_(list.begin()) , S_(list.size()) @@ -65,7 +65,7 @@ public: , S_(container.size()) { } - + template <size_t N> constexpr inline TArrayRef(T (&array)[N]) noexcept : T_(array) @@ -81,11 +81,11 @@ public: constexpr inline T* data() const noexcept { return T_; } - + constexpr inline size_t size() const noexcept { return S_; } - + constexpr size_t size_bytes() const noexcept { return (size() * sizeof(T)); } @@ -230,11 +230,11 @@ private: * * Named as its std counterparts, std::as_bytes. */ -template <typename T> +template <typename T> TArrayRef<const char> as_bytes(TArrayRef<T> arrayRef) noexcept { return TArrayRef<const char>( reinterpret_cast<const char*>(arrayRef.data()), - arrayRef.size_bytes()); + arrayRef.size_bytes()); } /** @@ -242,19 +242,19 @@ TArrayRef<const char> as_bytes(TArrayRef<T> arrayRef) noexcept { * * Named as its std counterparts, std::as_writable_bytes. */ -template <typename T> +template <typename T> TArrayRef<char> as_writable_bytes(TArrayRef<T> arrayRef) noexcept { return TArrayRef<char>( reinterpret_cast<char*>(arrayRef.data()), - arrayRef.size_bytes()); + arrayRef.size_bytes()); } -template <class Range> +template <class Range> constexpr TArrayRef<const typename Range::value_type> MakeArrayRef(const Range& range) { return TArrayRef<const typename Range::value_type>(range); } -template <class Range> +template <class Range> constexpr TArrayRef<typename Range::value_type> MakeArrayRef(Range& range) { return TArrayRef<typename Range::value_type>(range); } diff --git a/util/generic/array_ref_ut.cpp b/util/generic/array_ref_ut.cpp index ef367146e1..4c8eaf7135 100644 --- a/util/generic/array_ref_ut.cpp +++ b/util/generic/array_ref_ut.cpp @@ -142,10 +142,10 @@ Y_UNIT_TEST_SUITE(TestArrayRef) { Y_UNIT_TEST(TestEqualityOperator) { static constexpr size_t size = 5; - int a[size]{1, 2, 3, 4, 5}; - int b[size]{5, 4, 3, 2, 1}; - int c[size - 1]{5, 4, 3, 2}; - float d[size]{1.f, 2.f, 3.f, 4.f, 5.f}; + int a[size]{1, 2, 3, 4, 5}; + int b[size]{5, 4, 3, 2, 1}; + int c[size - 1]{5, 4, 3, 2}; + float d[size]{1.f, 2.f, 3.f, 4.f, 5.f}; TArrayRef<int> aRef(a); TConstArrayRef<int> aConstRef(a, size); @@ -212,7 +212,7 @@ Y_UNIT_TEST_SUITE(TestArrayRef) { //FIXME: size checks are implemented via Y_ASSERT, hence there is no way to test them } - + Y_UNIT_TEST(SubRegion) { TVector<char> x; for (size_t i = 0; i < 42; ++i) { @@ -238,7 +238,7 @@ Y_UNIT_TEST_SUITE(TestArrayRef) { UNIT_ASSERT_VALUES_EQUAL(bytesRef.size(), sizeof(int16_t) * constRef.size()); UNIT_ASSERT_EQUAL( bytesRef, - MakeArrayRef(std::vector<char>{0x01, 0x00, 0x02, 0x00, 0x03, 0x00})); + MakeArrayRef(std::vector<char>{0x01, 0x00, 0x02, 0x00, 0x03, 0x00})); //should not compile //as_writable_bytes(constRef); @@ -252,7 +252,7 @@ Y_UNIT_TEST_SUITE(TestArrayRef) { UNIT_ASSERT_VALUES_EQUAL(writableBytesRef.size(), sizeof(uint32_t)); UNIT_ASSERT_EQUAL( writableBytesRef, - MakeArrayRef(std::vector<char>{0x0e, 0x0d, 0x00, 0x0c})); + MakeArrayRef(std::vector<char>{0x0e, 0x0d, 0x00, 0x0c})); uint32_t newVal = 0xde'ad'be'ef; std::memcpy(writableBytesRef.data(), &newVal, writableBytesRef.size()); @@ -274,15 +274,15 @@ Y_UNIT_TEST_SUITE(TestArrayRef) { UNIT_ASSERT_VALUES_EQUAL(23, constRefFromNonConst[1]); } - static void Do(const TArrayRef<int> a) { - a[0] = 8; - } - + static void Do(const TArrayRef<int> a) { + a[0] = 8; + } + Y_UNIT_TEST(TestConst) { - int a[] = {1, 2}; - Do(a); - UNIT_ASSERT_VALUES_EQUAL(a[0], 8); - } + int a[] = {1, 2}; + Do(a); + UNIT_ASSERT_VALUES_EQUAL(a[0], 8); + } Y_UNIT_TEST(TestConstexpr) { static constexpr const int a[] = {1, 2, -3, -4}; @@ -290,11 +290,11 @@ Y_UNIT_TEST_SUITE(TestArrayRef) { static_assert(r0.size() == 1, "r0.size() is not equal 1"); static_assert(r0.data()[0] == 1, "r0.data()[0] is not equal to 1"); - static constexpr const TArrayRef<const int> r1{a}; + static constexpr const TArrayRef<const int> r1{a}; static_assert(r1.size() == 4, "r1.size() is not equal to 4"); static_assert(r1.data()[3] == -4, "r1.data()[3] is not equal to -4"); - static constexpr const TArrayRef<const int> r2 = r1; + static constexpr const TArrayRef<const int> r2 = r1; static_assert(r2.size() == 4, "r2.size() is not equal to 4"); static_assert(r2.data()[2] == -3, "r2.data()[2] is not equal to -3"); } diff --git a/util/generic/array_size.cpp b/util/generic/array_size.cpp index 0fdf17d686..763f96e4ed 100644 --- a/util/generic/array_size.cpp +++ b/util/generic/array_size.cpp @@ -1 +1 @@ -#include "array_size.h" +#include "array_size.h" diff --git a/util/generic/array_size.h b/util/generic/array_size.h index 1d4e6692c5..4d5f18ce63 100644 --- a/util/generic/array_size.h +++ b/util/generic/array_size.h @@ -1,24 +1,24 @@ -#pragma once - -#include <cstddef> - -namespace NArraySizePrivate { - template <class T> - struct TArraySize; - - template <class T, size_t N> - struct TArraySize<T[N]> { - enum { - Result = N - }; - }; - - template <class T, size_t N> - struct TArraySize<T (&)[N]> { - enum { - Result = N - }; - }; -} - +#pragma once + +#include <cstddef> + +namespace NArraySizePrivate { + template <class T> + struct TArraySize; + + template <class T, size_t N> + struct TArraySize<T[N]> { + enum { + Result = N + }; + }; + + template <class T, size_t N> + struct TArraySize<T (&)[N]> { + enum { + Result = N + }; + }; +} + #define Y_ARRAY_SIZE(arr) ((size_t)::NArraySizePrivate::TArraySize<decltype(arr)>::Result) diff --git a/util/generic/array_size_ut.cpp b/util/generic/array_size_ut.cpp index 01af91bb3d..13f45903c5 100644 --- a/util/generic/array_size_ut.cpp +++ b/util/generic/array_size_ut.cpp @@ -1,22 +1,22 @@ -#include "array_size.h" - +#include "array_size.h" + #include <library/cpp/testing/unittest/registar.h> - + Y_UNIT_TEST_SUITE(ArraySizeTest) { Y_UNIT_TEST(Test1) { - int x[100]; + int x[100]; Y_UNUSED(x); /* Make MSVC happy. */ - + UNIT_ASSERT_VALUES_EQUAL(Y_ARRAY_SIZE(x), 100); - } - + } + Y_UNIT_TEST(Test2) { - struct T { - }; - - T x[1]; + struct T { + }; + + T x[1]; Y_UNUSED(x); /* Make MSVC happy. */ - + UNIT_ASSERT_VALUES_EQUAL(Y_ARRAY_SIZE(x), 1); - } -} + } +} diff --git a/util/generic/benchmark/cont_speed/main.cpp b/util/generic/benchmark/cont_speed/main.cpp index 072f3e3114..01428c9974 100644 --- a/util/generic/benchmark/cont_speed/main.cpp +++ b/util/generic/benchmark/cont_speed/main.cpp @@ -1,117 +1,117 @@ -#include <library/cpp/testing/benchmark/bench.h> - -#include <util/generic/xrange.h> -#include <util/generic/string.h> -#include <util/generic/vector.h> -#include <util/generic/buffer.h> - -template <class C> -Y_NO_INLINE void Run(const C& c) { - for (size_t i = 0; i < c.size(); ++i) { - Y_DO_NOT_OPTIMIZE_AWAY(c[i]); - } -} - -template <class C> -void Do(size_t len, auto& iface) { - C c(len, 0); - - for (auto i : xrange(iface.Iterations())) { - Y_UNUSED(i); - Run(c); - } -} - -Y_CPU_BENCHMARK(TVector10, iface) { - Do<TVector<char>>(10, iface); -} - -Y_CPU_BENCHMARK(TVector100, iface) { - Do<TVector<char>>(100, iface); -} - -Y_CPU_BENCHMARK(TVector1000, iface) { - Do<TVector<char>>(1000, iface); -} - -Y_CPU_BENCHMARK(TString10, iface) { - Do<TString>(10, iface); -} - -Y_CPU_BENCHMARK(TString100, iface) { - Do<TString>(100, iface); -} - -Y_CPU_BENCHMARK(TString1000, iface) { - Do<TString>(1000, iface); -} - -Y_CPU_BENCHMARK(StdString10, iface) { - Do<std::string>(10, iface); -} - -Y_CPU_BENCHMARK(StdString100, iface) { - Do<std::string>(100, iface); -} - -Y_CPU_BENCHMARK(StdString1000, iface) { - Do<std::string>(1000, iface); -} - -struct TBuf: public TBuffer { - TBuf(size_t len, char v) { - for (size_t i = 0; i < len; ++i) { - Append(v); - } - } - - inline const auto& operator[](size_t i) const noexcept { - return *(data() + i); - } -}; - -Y_CPU_BENCHMARK(TBuffer10, iface) { - Do<TBuf>(10, iface); -} - -Y_CPU_BENCHMARK(TBuffer100, iface) { - Do<TBuf>(100, iface); -} - -Y_CPU_BENCHMARK(TBuffer1000, iface) { - Do<TBuf>(1000, iface); -} - -struct TArr { - inline TArr(size_t len, char ch) - : A(new char[len]) - , L(len) - { - for (size_t i = 0; i < L; ++i) { - A[i] = ch; - } - } - - inline const auto& operator[](size_t i) const noexcept { - return A[i]; - } - - inline size_t size() const noexcept { - return L; - } - - char* A; - size_t L; -}; - -Y_CPU_BENCHMARK(Pointer10, iface) { - Do<TArr>(10, iface); -} - -Y_CPU_BENCHMARK(Pointer100, iface) { - Do<TArr>(100, iface); -} - -Y_CPU_BENCHMARK(Pointer1000, iface) { - Do<TArr>(1000, iface); -} +#include <library/cpp/testing/benchmark/bench.h> + +#include <util/generic/xrange.h> +#include <util/generic/string.h> +#include <util/generic/vector.h> +#include <util/generic/buffer.h> + +template <class C> +Y_NO_INLINE void Run(const C& c) { + for (size_t i = 0; i < c.size(); ++i) { + Y_DO_NOT_OPTIMIZE_AWAY(c[i]); + } +} + +template <class C> +void Do(size_t len, auto& iface) { + C c(len, 0); + + for (auto i : xrange(iface.Iterations())) { + Y_UNUSED(i); + Run(c); + } +} + +Y_CPU_BENCHMARK(TVector10, iface) { + Do<TVector<char>>(10, iface); +} + +Y_CPU_BENCHMARK(TVector100, iface) { + Do<TVector<char>>(100, iface); +} + +Y_CPU_BENCHMARK(TVector1000, iface) { + Do<TVector<char>>(1000, iface); +} + +Y_CPU_BENCHMARK(TString10, iface) { + Do<TString>(10, iface); +} + +Y_CPU_BENCHMARK(TString100, iface) { + Do<TString>(100, iface); +} + +Y_CPU_BENCHMARK(TString1000, iface) { + Do<TString>(1000, iface); +} + +Y_CPU_BENCHMARK(StdString10, iface) { + Do<std::string>(10, iface); +} + +Y_CPU_BENCHMARK(StdString100, iface) { + Do<std::string>(100, iface); +} + +Y_CPU_BENCHMARK(StdString1000, iface) { + Do<std::string>(1000, iface); +} + +struct TBuf: public TBuffer { + TBuf(size_t len, char v) { + for (size_t i = 0; i < len; ++i) { + Append(v); + } + } + + inline const auto& operator[](size_t i) const noexcept { + return *(data() + i); + } +}; + +Y_CPU_BENCHMARK(TBuffer10, iface) { + Do<TBuf>(10, iface); +} + +Y_CPU_BENCHMARK(TBuffer100, iface) { + Do<TBuf>(100, iface); +} + +Y_CPU_BENCHMARK(TBuffer1000, iface) { + Do<TBuf>(1000, iface); +} + +struct TArr { + inline TArr(size_t len, char ch) + : A(new char[len]) + , L(len) + { + for (size_t i = 0; i < L; ++i) { + A[i] = ch; + } + } + + inline const auto& operator[](size_t i) const noexcept { + return A[i]; + } + + inline size_t size() const noexcept { + return L; + } + + char* A; + size_t L; +}; + +Y_CPU_BENCHMARK(Pointer10, iface) { + Do<TArr>(10, iface); +} + +Y_CPU_BENCHMARK(Pointer100, iface) { + Do<TArr>(100, iface); +} + +Y_CPU_BENCHMARK(Pointer1000, iface) { + Do<TArr>(1000, iface); +} diff --git a/util/generic/benchmark/cont_speed/ya.make b/util/generic/benchmark/cont_speed/ya.make index 67b3ae0bbe..6ff3fe767c 100644 --- a/util/generic/benchmark/cont_speed/ya.make +++ b/util/generic/benchmark/cont_speed/ya.make @@ -1,9 +1,9 @@ -Y_BENCHMARK() - -OWNER(g:util) - -SRCS( - main.cpp -) - -END() +Y_BENCHMARK() + +OWNER(g:util) + +SRCS( + main.cpp +) + +END() diff --git a/util/generic/benchmark/fastclp2/main.cpp b/util/generic/benchmark/fastclp2/main.cpp index 12578216e2..49277db077 100644 --- a/util/generic/benchmark/fastclp2/main.cpp +++ b/util/generic/benchmark/fastclp2/main.cpp @@ -11,8 +11,8 @@ namespace { template <typename T, size_t N> struct TExamplesHolder { TExamplesHolder() - : Examples(N) - { + : Examples(N) + { TFastRng<ui64> prng{42u * sizeof(T) * N}; for (auto& x : Examples) { x = prng(); @@ -23,7 +23,7 @@ namespace { }; } -#define DEFINE_BENCHMARK(type, count) \ +#define DEFINE_BENCHMARK(type, count) \ Y_CPU_BENCHMARK(FastClp2_##type##_##count, iface) { \ const auto& examples = Default<TExamplesHolder<type, count>>().Examples; \ for (const auto i : xrange(iface.Iterations())) { \ diff --git a/util/generic/benchmark/rotate_bits/main.cpp b/util/generic/benchmark/rotate_bits/main.cpp index 003cd29672..057edbe864 100644 --- a/util/generic/benchmark/rotate_bits/main.cpp +++ b/util/generic/benchmark/rotate_bits/main.cpp @@ -16,8 +16,8 @@ namespace { template <typename T, size_t N> struct TExamplesHolder { TExamplesHolder() - : Examples(N) - { + : Examples(N) + { TFastRng<ui64> prng{42u * sizeof(T) * N}; for (auto& e : Examples) { e.Value = prng(); diff --git a/util/generic/benchmark/singleton/f.cpp b/util/generic/benchmark/singleton/f.cpp index ada8c9f60a..bf6da53d9c 100644 --- a/util/generic/benchmark/singleton/f.cpp +++ b/util/generic/benchmark/singleton/f.cpp @@ -1,18 +1,18 @@ -#include <util/generic/singleton.h> - -struct X { - inline X() { - } - - char Buf[100]; -}; - -char& FF1() noexcept { - static X x; - - return x.Buf[0]; -} - -char& FF2() noexcept { - return Singleton<X>()->Buf[0]; -} +#include <util/generic/singleton.h> + +struct X { + inline X() { + } + + char Buf[100]; +}; + +char& FF1() noexcept { + static X x; + + return x.Buf[0]; +} + +char& FF2() noexcept { + return Singleton<X>()->Buf[0]; +} diff --git a/util/generic/benchmark/singleton/main.cpp b/util/generic/benchmark/singleton/main.cpp index 9bceca1b07..2b06bd371d 100644 --- a/util/generic/benchmark/singleton/main.cpp +++ b/util/generic/benchmark/singleton/main.cpp @@ -1,54 +1,54 @@ #include <library/cpp/testing/benchmark/bench.h> - -#include <util/generic/singleton.h> -#include <util/generic/xrange.h> - -char& FF1() noexcept; -char& FF2() noexcept; - -namespace { - struct X { - inline X() { - } - - char Buf[100]; - }; - - inline X& F1() noexcept { - static X x; - - return x; - } - - inline X& F2() noexcept { - return *Singleton<X>(); - } -} - -Y_CPU_BENCHMARK(MagicStatic, iface) { - for (const auto i : xrange(iface.Iterations())) { - Y_UNUSED(i); - Y_DO_NOT_OPTIMIZE_AWAY(F1().Buf); - } -} - -Y_CPU_BENCHMARK(Singleton, iface) { - for (const auto i : xrange(iface.Iterations())) { - Y_UNUSED(i); - Y_DO_NOT_OPTIMIZE_AWAY(F2().Buf); - } -} - -Y_CPU_BENCHMARK(MagicStaticNI, iface) { - for (const auto i : xrange(iface.Iterations())) { - Y_UNUSED(i); - Y_DO_NOT_OPTIMIZE_AWAY(FF1()); - } -} - -Y_CPU_BENCHMARK(SingletonNI, iface) { - for (const auto i : xrange(iface.Iterations())) { - Y_UNUSED(i); - Y_DO_NOT_OPTIMIZE_AWAY(FF2()); - } -} + +#include <util/generic/singleton.h> +#include <util/generic/xrange.h> + +char& FF1() noexcept; +char& FF2() noexcept; + +namespace { + struct X { + inline X() { + } + + char Buf[100]; + }; + + inline X& F1() noexcept { + static X x; + + return x; + } + + inline X& F2() noexcept { + return *Singleton<X>(); + } +} + +Y_CPU_BENCHMARK(MagicStatic, iface) { + for (const auto i : xrange(iface.Iterations())) { + Y_UNUSED(i); + Y_DO_NOT_OPTIMIZE_AWAY(F1().Buf); + } +} + +Y_CPU_BENCHMARK(Singleton, iface) { + for (const auto i : xrange(iface.Iterations())) { + Y_UNUSED(i); + Y_DO_NOT_OPTIMIZE_AWAY(F2().Buf); + } +} + +Y_CPU_BENCHMARK(MagicStaticNI, iface) { + for (const auto i : xrange(iface.Iterations())) { + Y_UNUSED(i); + Y_DO_NOT_OPTIMIZE_AWAY(FF1()); + } +} + +Y_CPU_BENCHMARK(SingletonNI, iface) { + for (const auto i : xrange(iface.Iterations())) { + Y_UNUSED(i); + Y_DO_NOT_OPTIMIZE_AWAY(FF2()); + } +} diff --git a/util/generic/benchmark/singleton/ya.make b/util/generic/benchmark/singleton/ya.make index d34e0863fa..12d3d316c8 100644 --- a/util/generic/benchmark/singleton/ya.make +++ b/util/generic/benchmark/singleton/ya.make @@ -1,11 +1,11 @@ Y_BENCHMARK() - + OWNER(g:util) SUBSCRIBER(g:util-subscribers) - -SRCS( - f.cpp - main.cpp -) - -END() + +SRCS( + f.cpp + main.cpp +) + +END() diff --git a/util/generic/benchmark/smart_pointers/main.cpp b/util/generic/benchmark/smart_pointers/main.cpp index aa04601807..92c2f923bb 100644 --- a/util/generic/benchmark/smart_pointers/main.cpp +++ b/util/generic/benchmark/smart_pointers/main.cpp @@ -1,14 +1,14 @@ #include <library/cpp/testing/benchmark/bench.h> - -#include <util/generic/ptr.h> -#include <util/generic/xrange.h> - -struct X: public TAtomicRefCount<X> { -}; - -Y_CPU_BENCHMARK(SimplePtrConstruct, iface) { - for (const auto i : xrange(iface.Iterations())) { - Y_UNUSED(i); - Y_DO_NOT_OPTIMIZE_AWAY(TSimpleIntrusivePtr<X>()); - } -} + +#include <util/generic/ptr.h> +#include <util/generic/xrange.h> + +struct X: public TAtomicRefCount<X> { +}; + +Y_CPU_BENCHMARK(SimplePtrConstruct, iface) { + for (const auto i : xrange(iface.Iterations())) { + Y_UNUSED(i); + Y_DO_NOT_OPTIMIZE_AWAY(TSimpleIntrusivePtr<X>()); + } +} diff --git a/util/generic/benchmark/smart_pointers/ya.make b/util/generic/benchmark/smart_pointers/ya.make index bd830bbe1d..7059abc3a4 100644 --- a/util/generic/benchmark/smart_pointers/ya.make +++ b/util/generic/benchmark/smart_pointers/ya.make @@ -1,10 +1,10 @@ Y_BENCHMARK() - + OWNER(g:util) SUBSCRIBER(g:util-subscribers) - -SRCS( - main.cpp -) - -END() + +SRCS( + main.cpp +) + +END() diff --git a/util/generic/benchmark/sort/main.cpp b/util/generic/benchmark/sort/main.cpp index 48fbd2052a..d58f491f4d 100644 --- a/util/generic/benchmark/sort/main.cpp +++ b/util/generic/benchmark/sort/main.cpp @@ -1,77 +1,77 @@ #include <library/cpp/testing/benchmark/bench.h> - -#include <util/generic/algorithm.h> -#include <util/generic/vector.h> -#include <util/generic/xrange.h> - -Y_CPU_BENCHMARK(Sort1, iface) { + +#include <util/generic/algorithm.h> +#include <util/generic/vector.h> +#include <util/generic/xrange.h> + +Y_CPU_BENCHMARK(Sort1, iface) { TVector<int> x = {1}; - - for (const auto i : xrange(iface.Iterations())) { - Y_UNUSED(i); - Sort(x); - } -} - -Y_CPU_BENCHMARK(Sort2, iface) { + + for (const auto i : xrange(iface.Iterations())) { + Y_UNUSED(i); + Sort(x); + } +} + +Y_CPU_BENCHMARK(Sort2, iface) { TVector<int> x = {2, 1}; - - for (const auto i : xrange(iface.Iterations())) { - Y_UNUSED(i); - Sort(x); - } -} - -Y_CPU_BENCHMARK(Sort4, iface) { + + for (const auto i : xrange(iface.Iterations())) { + Y_UNUSED(i); + Sort(x); + } +} + +Y_CPU_BENCHMARK(Sort4, iface) { TVector<int> x = {4, 3, 2, 1}; - - for (const auto i : xrange(iface.Iterations())) { - Y_UNUSED(i); - Sort(x); - } -} - -Y_CPU_BENCHMARK(Sort16, iface) { + + for (const auto i : xrange(iface.Iterations())) { + Y_UNUSED(i); + Sort(x); + } +} + +Y_CPU_BENCHMARK(Sort16, iface) { TVector<int> x = {16, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1}; - - for (const auto i : xrange(iface.Iterations())) { - Y_UNUSED(i); - Sort(x); - } -} - -Y_CPU_BENCHMARK(StableSort1, iface) { + + for (const auto i : xrange(iface.Iterations())) { + Y_UNUSED(i); + Sort(x); + } +} + +Y_CPU_BENCHMARK(StableSort1, iface) { TVector<int> x = {1}; - - for (const auto i : xrange(iface.Iterations())) { - Y_UNUSED(i); - StableSort(x); - } -} - -Y_CPU_BENCHMARK(StableSort2, iface) { + + for (const auto i : xrange(iface.Iterations())) { + Y_UNUSED(i); + StableSort(x); + } +} + +Y_CPU_BENCHMARK(StableSort2, iface) { TVector<int> x = {2, 1}; - - for (const auto i : xrange(iface.Iterations())) { - Y_UNUSED(i); - StableSort(x); - } -} - -Y_CPU_BENCHMARK(StableSort4, iface) { + + for (const auto i : xrange(iface.Iterations())) { + Y_UNUSED(i); + StableSort(x); + } +} + +Y_CPU_BENCHMARK(StableSort4, iface) { TVector<int> x = {4, 3, 2, 1}; - - for (const auto i : xrange(iface.Iterations())) { - Y_UNUSED(i); - StableSort(x); - } -} - -Y_CPU_BENCHMARK(StableSort16, iface) { + + for (const auto i : xrange(iface.Iterations())) { + Y_UNUSED(i); + StableSort(x); + } +} + +Y_CPU_BENCHMARK(StableSort16, iface) { TVector<int> x = {16, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1}; - - for (const auto i : xrange(iface.Iterations())) { - Y_UNUSED(i); - StableSort(x); - } -} + + for (const auto i : xrange(iface.Iterations())) { + Y_UNUSED(i); + StableSort(x); + } +} diff --git a/util/generic/benchmark/sort/ya.make b/util/generic/benchmark/sort/ya.make index bd830bbe1d..7059abc3a4 100644 --- a/util/generic/benchmark/sort/ya.make +++ b/util/generic/benchmark/sort/ya.make @@ -1,10 +1,10 @@ Y_BENCHMARK() - + OWNER(g:util) SUBSCRIBER(g:util-subscribers) - -SRCS( - main.cpp -) - -END() + +SRCS( + main.cpp +) + +END() diff --git a/util/generic/benchmark/string/benchmarks.h b/util/generic/benchmark/string/benchmarks.h index 5420e75817..e347d7ff47 100644 --- a/util/generic/benchmark/string/benchmarks.h +++ b/util/generic/benchmark/string/benchmarks.h @@ -15,8 +15,8 @@ namespace { const auto defaultString = TBenchmarkedClass(); const auto emptyString = TBenchmarkedClass(""); - const auto lengthOneString = TBenchmarkedClass("1"); - const auto length1KString = TBenchmarkedClass(1000, '1'); + const auto lengthOneString = TBenchmarkedClass("1"); + const auto length1KString = TBenchmarkedClass(1000, '1'); Y_CPU_PREFIXED_BENCHMARK(BENCHMARK_PREFIX, CreateDefault, iface) { for (const auto i : xrange(iface.Iterations())) { diff --git a/util/generic/benchmark/ya.make b/util/generic/benchmark/ya.make index e477a02415..635860a646 100644 --- a/util/generic/benchmark/ya.make +++ b/util/generic/benchmark/ya.make @@ -1,5 +1,5 @@ -OWNER(yazevnul g:util) - +OWNER(yazevnul g:util) + SUBSCRIBER(g:util-subscribers) RECURSE( @@ -10,10 +10,10 @@ RECURSE( rotate_bits rotate_bits/metrics singleton - smart_pointers - sort + smart_pointers + sort string vector_count_ctor - vector_count_ctor/metrics - cont_speed + vector_count_ctor/metrics + cont_speed ) diff --git a/util/generic/bitmap.cpp b/util/generic/bitmap.cpp index 74cb2cf4d2..a629a870d0 100644 --- a/util/generic/bitmap.cpp +++ b/util/generic/bitmap.cpp @@ -1 +1 @@ -#include "bitmap.h" +#include "bitmap.h" diff --git a/util/generic/bitmap.h b/util/generic/bitmap.h index 725fa61b81..f77d182460 100644 --- a/util/generic/bitmap.h +++ b/util/generic/bitmap.h @@ -1,300 +1,300 @@ #pragma once #include "fwd.h" -#include "ptr.h" -#include "bitops.h" +#include "ptr.h" +#include "bitops.h" #include "typetraits.h" -#include "algorithm.h" +#include "algorithm.h" #include "utility.h" - -#include <util/system/yassert.h> -#include <util/system/defaults.h> + +#include <util/system/yassert.h> +#include <util/system/defaults.h> #include <util/str_stl.h> #include <util/ysaveload.h> namespace NBitMapPrivate { - // Returns number of bits set; result is in most significatnt byte - inline ui64 ByteSums(ui64 x) { - ui64 byteSums = x - ((x & 0xAAAAAAAAAAAAAAAAULL) >> 1); - - byteSums = (byteSums & 0x3333333333333333ULL) + ((byteSums >> 2) & 0x3333333333333333ULL); - byteSums = (byteSums + (byteSums >> 4)) & 0x0F0F0F0F0F0F0F0FULL; - - return byteSums * 0x0101010101010101ULL; - } - - // better than intrinsics without -mpopcnt - template <typename T> + // Returns number of bits set; result is in most significatnt byte + inline ui64 ByteSums(ui64 x) { + ui64 byteSums = x - ((x & 0xAAAAAAAAAAAAAAAAULL) >> 1); + + byteSums = (byteSums & 0x3333333333333333ULL) + ((byteSums >> 2) & 0x3333333333333333ULL); + byteSums = (byteSums + (byteSums >> 4)) & 0x0F0F0F0F0F0F0F0FULL; + + return byteSums * 0x0101010101010101ULL; + } + + // better than intrinsics without -mpopcnt + template <typename T> static unsigned CountBitsPrivate(T v) noexcept { - return static_cast<unsigned>(ByteSums(v) >> 56); - } - - template <typename TChunkType, size_t ExtraBits> - struct TSanitizeMask { + return static_cast<unsigned>(ByteSums(v) >> 56); + } + + template <typename TChunkType, size_t ExtraBits> + struct TSanitizeMask { static constexpr TChunkType Value = ~((~TChunkType(0)) << ExtraBits); - }; + }; - template <typename TChunkType> - struct TSanitizeMask<TChunkType, 0> { + template <typename TChunkType> + struct TSanitizeMask<TChunkType, 0> { static constexpr TChunkType Value = (TChunkType)~TChunkType(0u); - }; + }; - template <typename TTargetChunk, typename TSourceChunk> - struct TBigToSmallDataCopier { - static_assert(sizeof(TTargetChunk) < sizeof(TSourceChunk), "expect sizeof(TTargetChunk) < sizeof(TSourceChunk)"); - static_assert(0 == sizeof(TSourceChunk) % sizeof(TTargetChunk), "expect 0 == sizeof(TSourceChunk) % sizeof(TTargetChunk)"); + template <typename TTargetChunk, typename TSourceChunk> + struct TBigToSmallDataCopier { + static_assert(sizeof(TTargetChunk) < sizeof(TSourceChunk), "expect sizeof(TTargetChunk) < sizeof(TSourceChunk)"); + static_assert(0 == sizeof(TSourceChunk) % sizeof(TTargetChunk), "expect 0 == sizeof(TSourceChunk) % sizeof(TTargetChunk)"); static constexpr size_t BLOCK_SIZE = sizeof(TSourceChunk) / sizeof(TTargetChunk); - union TCnv { - TSourceChunk BigData; - TTargetChunk SmallData[BLOCK_SIZE]; - }; + union TCnv { + TSourceChunk BigData; + TTargetChunk SmallData[BLOCK_SIZE]; + }; - static inline void CopyChunk(TTargetChunk* target, TSourceChunk source) { - TCnv c; - c.BigData = source; + static inline void CopyChunk(TTargetChunk* target, TSourceChunk source) { + TCnv c; + c.BigData = source; #if defined(_big_endian_) ::ReverseCopy(c.SmallData, c.SmallData + Y_ARRAY_SIZE(c.SmallData), target); #else ::Copy(c.SmallData, c.SmallData + Y_ARRAY_SIZE(c.SmallData), target); #endif - } + } - static inline void Copy(TTargetChunk* target, size_t targetSize, const TSourceChunk* source, size_t sourceSize) { + static inline void Copy(TTargetChunk* target, size_t targetSize, const TSourceChunk* source, size_t sourceSize) { Y_ASSERT(targetSize >= sourceSize * BLOCK_SIZE); - if (targetSize > sourceSize * BLOCK_SIZE) { - ::Fill(target + sourceSize * BLOCK_SIZE, target + targetSize, 0); - } - for (size_t i = 0; i < sourceSize; ++i) { - CopyChunk(target + i * BLOCK_SIZE, source[i]); - } + if (targetSize > sourceSize * BLOCK_SIZE) { + ::Fill(target + sourceSize * BLOCK_SIZE, target + targetSize, 0); + } + for (size_t i = 0; i < sourceSize; ++i) { + CopyChunk(target + i * BLOCK_SIZE, source[i]); + } } - }; + }; - template <typename TTargetChunk, typename TSourceChunk> - struct TSmallToBigDataCopier { - static_assert(sizeof(TTargetChunk) > sizeof(TSourceChunk), "expect sizeof(TTargetChunk) > sizeof(TSourceChunk)"); - static_assert(0 == sizeof(TTargetChunk) % sizeof(TSourceChunk), "expect 0 == sizeof(TTargetChunk) % sizeof(TSourceChunk)"); + template <typename TTargetChunk, typename TSourceChunk> + struct TSmallToBigDataCopier { + static_assert(sizeof(TTargetChunk) > sizeof(TSourceChunk), "expect sizeof(TTargetChunk) > sizeof(TSourceChunk)"); + static_assert(0 == sizeof(TTargetChunk) % sizeof(TSourceChunk), "expect 0 == sizeof(TTargetChunk) % sizeof(TSourceChunk)"); static constexpr size_t BLOCK_SIZE = sizeof(TTargetChunk) / sizeof(TSourceChunk); - union TCnv { - TSourceChunk SmallData[BLOCK_SIZE]; - TTargetChunk BigData; - }; + union TCnv { + TSourceChunk SmallData[BLOCK_SIZE]; + TTargetChunk BigData; + }; - static inline TTargetChunk CopyFullChunk(const TSourceChunk* source) { - TCnv c; + static inline TTargetChunk CopyFullChunk(const TSourceChunk* source) { + TCnv c; #if defined(_big_endian_) - ::ReverseCopy(source, source + BLOCK_SIZE, c.SmallData); + ::ReverseCopy(source, source + BLOCK_SIZE, c.SmallData); #else - ::Copy(source, source + BLOCK_SIZE, c.SmallData); + ::Copy(source, source + BLOCK_SIZE, c.SmallData); #endif - return c.BigData; - } + return c.BigData; + } - static inline TTargetChunk CopyPartChunk(const TSourceChunk* source, size_t count) { + static inline TTargetChunk CopyPartChunk(const TSourceChunk* source, size_t count) { Y_ASSERT(count <= BLOCK_SIZE); - TCnv c; - c.BigData = 0; + TCnv c; + c.BigData = 0; #if defined(_big_endian_) - ::ReverseCopy(source, source + count, c.SmallData); + ::ReverseCopy(source, source + count, c.SmallData); #else - ::Copy(source, source + count, c.SmallData); + ::Copy(source, source + count, c.SmallData); #endif - return c.BigData; - } + return c.BigData; + } - static inline void Copy(TTargetChunk* target, size_t targetSize, const TSourceChunk* source, size_t sourceSize) { + static inline void Copy(TTargetChunk* target, size_t targetSize, const TSourceChunk* source, size_t sourceSize) { Y_ASSERT(targetSize * BLOCK_SIZE >= sourceSize); - if (targetSize * BLOCK_SIZE > sourceSize) { - ::Fill(target + sourceSize / BLOCK_SIZE, target + targetSize, 0); - } - size_t i = 0; - for (; i < sourceSize / BLOCK_SIZE; ++i) { - target[i] = CopyFullChunk(source + i * BLOCK_SIZE); - } - if (0 != sourceSize % BLOCK_SIZE) { - target[i] = CopyPartChunk(source + i * BLOCK_SIZE, sourceSize % BLOCK_SIZE); - } + if (targetSize * BLOCK_SIZE > sourceSize) { + ::Fill(target + sourceSize / BLOCK_SIZE, target + targetSize, 0); + } + size_t i = 0; + for (; i < sourceSize / BLOCK_SIZE; ++i) { + target[i] = CopyFullChunk(source + i * BLOCK_SIZE); + } + if (0 != sourceSize % BLOCK_SIZE) { + target[i] = CopyPartChunk(source + i * BLOCK_SIZE, sourceSize % BLOCK_SIZE); + } } - }; + }; - template <typename TChunk> - struct TUniformDataCopier { - static inline void Copy(TChunk* target, size_t targetSize, const TChunk* source, size_t sourceSize) { + template <typename TChunk> + struct TUniformDataCopier { + static inline void Copy(TChunk* target, size_t targetSize, const TChunk* source, size_t sourceSize) { Y_ASSERT(targetSize >= sourceSize); - for (size_t i = 0; i < sourceSize; ++i) { - target[i] = source[i]; - } - for (size_t i = sourceSize; i < targetSize; ++i) { - target[i] = 0; - } + for (size_t i = 0; i < sourceSize; ++i) { + target[i] = source[i]; + } + for (size_t i = sourceSize; i < targetSize; ++i) { + target[i] = 0; + } } - }; + }; - template <typename TFirst, typename TSecond> - struct TIsSmaller { - enum { - Result = sizeof(TFirst) < sizeof(TSecond) - }; + template <typename TFirst, typename TSecond> + struct TIsSmaller { + enum { + Result = sizeof(TFirst) < sizeof(TSecond) + }; }; - template <typename TTargetChunk, typename TSourceChunk> + template <typename TTargetChunk, typename TSourceChunk> struct TDataCopier: public std::conditional_t<std::is_same<TTargetChunk, TSourceChunk>::value, TUniformDataCopier<TTargetChunk>, std::conditional_t<TIsSmaller<TTargetChunk, TSourceChunk>::Result, TBigToSmallDataCopier<TTargetChunk, TSourceChunk>, TSmallToBigDataCopier<TTargetChunk, TSourceChunk>>> { - }; + }; - template <typename TTargetChunk, typename TSourceChunk> - inline void CopyData(TTargetChunk* target, size_t targetSize, const TSourceChunk* source, size_t sourceSize) { - TDataCopier<TTargetChunk, TSourceChunk>::Copy(target, targetSize, source, sourceSize); - } + template <typename TTargetChunk, typename TSourceChunk> + inline void CopyData(TTargetChunk* target, size_t targetSize, const TSourceChunk* source, size_t sourceSize) { + TDataCopier<TTargetChunk, TSourceChunk>::Copy(target, targetSize, source, sourceSize); + } - template <size_t BitCount, typename TChunkType> - struct TFixedStorage { + template <size_t BitCount, typename TChunkType> + struct TFixedStorage { using TChunk = TChunkType; static constexpr size_t Size = (BitCount + 8 * sizeof(TChunk) - 1) / (8 * sizeof(TChunk)); - TChunk Data[Size]; + TChunk Data[Size]; - TFixedStorage() { - Zero(Data); - } + TFixedStorage() { + Zero(Data); + } - TFixedStorage(const TFixedStorage<BitCount, TChunkType>& st) { - for (size_t i = 0; i < Size; ++i) { - Data[i] = st.Data[i]; - } - } + TFixedStorage(const TFixedStorage<BitCount, TChunkType>& st) { + for (size_t i = 0; i < Size; ++i) { + Data[i] = st.Data[i]; + } + } - template <typename TOtherChunk> - TFixedStorage(const TOtherChunk* data, size_t size) { + template <typename TOtherChunk> + TFixedStorage(const TOtherChunk* data, size_t size) { Y_VERIFY(Size * sizeof(TChunk) >= size * sizeof(TOtherChunk), "Exceeding bitmap storage capacity"); - CopyData(Data, Size, data, size); + CopyData(Data, Size, data, size); } Y_FORCE_INLINE void Swap(TFixedStorage<BitCount, TChunkType>& st) { - for (size_t i = 0; i < Size; ++i) { - DoSwap(Data[i], st.Data[i]); - } - } + for (size_t i = 0; i < Size; ++i) { + DoSwap(Data[i], st.Data[i]); + } + } Y_FORCE_INLINE static constexpr size_t GetBitCapacity() noexcept { - return BitCount; + return BitCount; } Y_FORCE_INLINE static constexpr size_t GetChunkCapacity() noexcept { - return Size; - } + return Size; + } - // Returns true if the resulting storage capacity is enough to fit the requested size + // Returns true if the resulting storage capacity is enough to fit the requested size Y_FORCE_INLINE static constexpr bool ExpandBitSize(const size_t bitSize) noexcept { - return bitSize <= BitCount; - } + return bitSize <= BitCount; + } Y_FORCE_INLINE void Sanitize() { - Data[Size - 1] &= TSanitizeMask<TChunk, BitCount % (8 * sizeof(TChunk))>::Value; - } - }; - - // Dynamically expanded storage. - // It uses "on stack" realization with no allocation for one chunk spaces - template <typename TChunkType> - struct TDynamicStorage { + Data[Size - 1] &= TSanitizeMask<TChunk, BitCount % (8 * sizeof(TChunk))>::Value; + } + }; + + // Dynamically expanded storage. + // It uses "on stack" realization with no allocation for one chunk spaces + template <typename TChunkType> + struct TDynamicStorage { using TChunk = TChunkType; - size_t Size; - TChunk StackData; - TArrayHolder<TChunk> ArrayData; - TChunk* Data; - - TDynamicStorage() - : Size(1) - , StackData(0) - , Data(&StackData) - { - } - - TDynamicStorage(const TDynamicStorage<TChunk>& st) - : Size(1) - , StackData(0) - , Data(&StackData) - { - ExpandSize(st.Size, false); - for (size_t i = 0; i < st.Size; ++i) { - Data[i] = st.Data[i]; - } - for (size_t i = st.Size; i < Size; ++i) { - Data[i] = 0; - } - } - - template <typename TOtherChunk> - TDynamicStorage(const TOtherChunk* data, size_t size) - : Size(1) - , StackData(0) - , Data(&StackData) - { - ExpandBitSize(size * sizeof(TOtherChunk) * 8, false); - CopyData(Data, Size, data, size); + size_t Size; + TChunk StackData; + TArrayHolder<TChunk> ArrayData; + TChunk* Data; + + TDynamicStorage() + : Size(1) + , StackData(0) + , Data(&StackData) + { + } + + TDynamicStorage(const TDynamicStorage<TChunk>& st) + : Size(1) + , StackData(0) + , Data(&StackData) + { + ExpandSize(st.Size, false); + for (size_t i = 0; i < st.Size; ++i) { + Data[i] = st.Data[i]; + } + for (size_t i = st.Size; i < Size; ++i) { + Data[i] = 0; + } + } + + template <typename TOtherChunk> + TDynamicStorage(const TOtherChunk* data, size_t size) + : Size(1) + , StackData(0) + , Data(&StackData) + { + ExpandBitSize(size * sizeof(TOtherChunk) * 8, false); + CopyData(Data, Size, data, size); } - + Y_FORCE_INLINE void Swap(TDynamicStorage<TChunkType>& st) { - DoSwap(Size, st.Size); - DoSwap(StackData, st.StackData); - DoSwap(ArrayData, st.ArrayData); - Data = 1 == Size ? &StackData : ArrayData.Get(); - st.Data = 1 == st.Size ? &st.StackData : st.ArrayData.Get(); + DoSwap(Size, st.Size); + DoSwap(StackData, st.StackData); + DoSwap(ArrayData, st.ArrayData); + Data = 1 == Size ? &StackData : ArrayData.Get(); + st.Data = 1 == st.Size ? &st.StackData : st.ArrayData.Get(); } Y_FORCE_INLINE size_t GetBitCapacity() const { - return Size * 8 * sizeof(TChunk); - } + return Size * 8 * sizeof(TChunk); + } Y_FORCE_INLINE size_t GetChunkCapacity() const { - return Size; - } + return Size; + } - // Returns true if the resulting storage capacity is enough to fit the requested size + // Returns true if the resulting storage capacity is enough to fit the requested size Y_FORCE_INLINE bool ExpandSize(size_t size, bool keepData = true) { - if (size > Size) { + if (size > Size) { size = Max(size, Size * 2); - TArrayHolder<TChunk> newData(new TChunk[size]); - if (keepData) { - for (size_t i = 0; i < Size; ++i) { - newData[i] = Data[i]; - } - for (size_t i = Size; i < size; ++i) { - newData[i] = 0; - } + TArrayHolder<TChunk> newData(new TChunk[size]); + if (keepData) { + for (size_t i = 0; i < Size; ++i) { + newData[i] = Data[i]; + } + for (size_t i = Size; i < size; ++i) { + newData[i] = 0; + } } - DoSwap(ArrayData, newData); - Data = ArrayData.Get(); - Size = size; + DoSwap(ArrayData, newData); + Data = ArrayData.Get(); + Size = size; } - return true; + return true; } Y_FORCE_INLINE bool ExpandBitSize(size_t bitSize, bool keepData = true) { - return ExpandSize((bitSize + 8 * sizeof(TChunk) - 1) / (8 * sizeof(TChunk)), keepData); - } + return ExpandSize((bitSize + 8 * sizeof(TChunk) - 1) / (8 * sizeof(TChunk)), keepData); + } Y_FORCE_INLINE void Sanitize() { - } - }; + } + }; - template <size_t num> - struct TDivCount { + template <size_t num> + struct TDivCount { static constexpr size_t Value = 1 + TDivCount<(num >> 1)>::Value; - }; + }; - template <> - struct TDivCount<0> { + template <> + struct TDivCount<0> { static constexpr size_t Value = 0; - }; + }; -} +} template <size_t BitCount, typename TChunkType> struct TFixedBitMapTraits { @@ -322,8 +322,8 @@ private: static constexpr size_t DivCount = NBitMapPrivate::TDivCount<BitsPerChunk>::Value - 1; static constexpr TChunk FullChunk = (TChunk)~TChunk(0); - template <class> - friend class TBitMapOps; + template <class> + friend class TBitMapOps; using TStorage = typename TTraits::TStorage; @@ -418,7 +418,7 @@ private: public: TBitMapOps() = default; - TBitMapOps(TChunk val) { + TBitMapOps(TChunk val) { Mask.Data[0] = val; Mask.Sanitize(); } @@ -489,11 +489,11 @@ public: } Y_FORCE_INLINE TThis& operator<<=(size_t pos) { - return LShift(pos); + return LShift(pos); } Y_FORCE_INLINE TThis& operator>>=(size_t pos) { - return RShift(pos); + return RShift(pos); } Y_FORCE_INLINE TThis operator<<(size_t pos) const { @@ -565,7 +565,7 @@ public: return false; } - template <class TTo> + template <class TTo> void Export(size_t pos, TTo& to) const { static_assert(std::is_unsigned<TTo>::value, "expect std::is_unsigned<TTo>::value"); to = 0; @@ -625,10 +625,10 @@ public: --nonZeroChunk; return nonZeroChunk || Mask.Data[nonZeroChunk] ? nonZeroChunk * BitsPerChunk + GetValueBitCount(TIntType(Mask.Data[nonZeroChunk])) - : 0; + : 0; } - Y_PURE_FUNCTION Y_FORCE_INLINE bool Empty() const { + Y_PURE_FUNCTION Y_FORCE_INLINE bool Empty() const { for (size_t i = 0; i < Mask.GetChunkCapacity(); ++i) if (Mask.Data[i]) return false; @@ -862,7 +862,7 @@ public: if (0 != Mask.Data[i]) return false; } - } else if (Mask.GetChunkCapacity() < bitmap.Mask.GetChunkCapacity()) { + } else if (Mask.GetChunkCapacity() < bitmap.Mask.GetChunkCapacity()) { for (size_t i = Mask.GetChunkCapacity(); i < bitmap.Mask.GetChunkCapacity(); ++i) { if (0 != bitmap.Mask.Data[i]) return false; @@ -928,7 +928,7 @@ public: // } // See Y_FOR_EACH_BIT macro definition at the bottom size_t NextNonZeroBit(size_t pos) const { - size_t i = (pos + 1) >> DivCount; + size_t i = (pos + 1) >> DivCount; if (i < Mask.GetChunkCapacity()) { const size_t offset = (pos + 1) & ModMask; // Process the current chunk @@ -954,7 +954,7 @@ public: Y_FORCE_INLINE size_t Count() const { size_t count = 0; for (size_t i = 0; i < Mask.GetChunkCapacity(); ++i) - count += ::NBitMapPrivate::CountBitsPrivate(Mask.Data[i]); + count += ::NBitMapPrivate::CountBitsPrivate(Mask.Data[i]); return count; } @@ -1011,77 +1011,77 @@ public: }; template <class X, class Y> -inline TBitMapOps<X> operator&(const TBitMapOps<X>& x, const TBitMapOps<Y>& y) { +inline TBitMapOps<X> operator&(const TBitMapOps<X>& x, const TBitMapOps<Y>& y) { return TBitMapOps<X>(x).And(y); } template <class X> -inline TBitMapOps<X> operator&(const TBitMapOps<X>& x, const typename TBitMapOps<X>::TChunk& y) { +inline TBitMapOps<X> operator&(const TBitMapOps<X>& x, const typename TBitMapOps<X>::TChunk& y) { return TBitMapOps<X>(x).And(y); } template <class X> -inline TBitMapOps<X> operator&(const typename TBitMapOps<X>::TChunk& x, const TBitMapOps<X>& y) { +inline TBitMapOps<X> operator&(const typename TBitMapOps<X>::TChunk& x, const TBitMapOps<X>& y) { return TBitMapOps<X>(x).And(y); } template <class X, class Y> -inline TBitMapOps<X> operator|(const TBitMapOps<X>& x, const TBitMapOps<Y>& y) { +inline TBitMapOps<X> operator|(const TBitMapOps<X>& x, const TBitMapOps<Y>& y) { return TBitMapOps<X>(x).Or(y); } template <class X> -inline TBitMapOps<X> operator|(const TBitMapOps<X>& x, const typename TBitMapOps<X>::TChunk& y) { +inline TBitMapOps<X> operator|(const TBitMapOps<X>& x, const typename TBitMapOps<X>::TChunk& y) { return TBitMapOps<X>(x).Or(y); } template <class X> -inline TBitMapOps<X> operator|(const typename TBitMapOps<X>::TChunk& x, const TBitMapOps<X>& y) { +inline TBitMapOps<X> operator|(const typename TBitMapOps<X>::TChunk& x, const TBitMapOps<X>& y) { return TBitMapOps<X>(x).Or(y); } template <class X, class Y> -inline TBitMapOps<X> operator^(const TBitMapOps<X>& x, const TBitMapOps<Y>& y) { +inline TBitMapOps<X> operator^(const TBitMapOps<X>& x, const TBitMapOps<Y>& y) { return TBitMapOps<X>(x).Xor(y); } template <class X> -inline TBitMapOps<X> operator^(const TBitMapOps<X>& x, const typename TBitMapOps<X>::TChunk& y) { +inline TBitMapOps<X> operator^(const TBitMapOps<X>& x, const typename TBitMapOps<X>::TChunk& y) { return TBitMapOps<X>(x).Xor(y); } template <class X> -inline TBitMapOps<X> operator^(const typename TBitMapOps<X>::TChunk& x, const TBitMapOps<X>& y) { +inline TBitMapOps<X> operator^(const typename TBitMapOps<X>::TChunk& x, const TBitMapOps<X>& y) { return TBitMapOps<X>(x).Xor(y); } template <class X, class Y> -inline TBitMapOps<X> operator-(const TBitMapOps<X>& x, const TBitMapOps<Y>& y) { +inline TBitMapOps<X> operator-(const TBitMapOps<X>& x, const TBitMapOps<Y>& y) { return TBitMapOps<X>(x).SetDifference(y); } template <class X> -inline TBitMapOps<X> operator-(const TBitMapOps<X>& x, const typename TBitMapOps<X>::TChunk& y) { +inline TBitMapOps<X> operator-(const TBitMapOps<X>& x, const typename TBitMapOps<X>::TChunk& y) { return TBitMapOps<X>(x).SetDifference(y); } template <class X> -inline TBitMapOps<X> operator-(const typename TBitMapOps<X>::TChunk& x, const TBitMapOps<X>& y) { +inline TBitMapOps<X> operator-(const typename TBitMapOps<X>::TChunk& x, const TBitMapOps<X>& y) { return TBitMapOps<X>(x).SetDifference(y); } template <class X> -inline TBitMapOps<X> operator~(const TBitMapOps<X>& x) { +inline TBitMapOps<X> operator~(const TBitMapOps<X>& x) { return TBitMapOps<X>(x).Flip(); } /////////////////// Specialization /////////////////////////// template <size_t BitCount, typename TChunkType /*= ui64*/> -class TBitMap: public TBitMapOps<TFixedBitMapTraits<BitCount, TChunkType>> { +class TBitMap: public TBitMapOps<TFixedBitMapTraits<BitCount, TChunkType>> { private: using TBase = TBitMapOps<TFixedBitMapTraits<BitCount, TChunkType>>; - + public: TBitMap() : TBase() @@ -1107,7 +1107,7 @@ using TDynBitMap = TBitMapOps<TDynamicBitMapTraits<ui64>>; #define Y_FOR_EACH_BIT(var, bitmap) for (size_t var = (bitmap).FirstNonZeroBit(); var != (bitmap).Size(); var = (bitmap).NextNonZeroBit(var)) template <typename TTraits> -struct THash<TBitMapOps<TTraits>> { +struct THash<TBitMapOps<TTraits>> { size_t operator()(const TBitMapOps<TTraits>& elem) const { return elem.Hash(); } diff --git a/util/generic/bitmap_ut.cpp b/util/generic/bitmap_ut.cpp index 82443c6a3c..087d34a8dc 100644 --- a/util/generic/bitmap_ut.cpp +++ b/util/generic/bitmap_ut.cpp @@ -1,47 +1,47 @@ -#include "bitmap.h" - +#include "bitmap.h" + #include <library/cpp/testing/unittest/registar.h> -#define INIT_BITMAP(bitmap, bits) \ +#define INIT_BITMAP(bitmap, bits) \ for (size_t i = 0; i < sizeof(bits) / sizeof(size_t); ++i) { \ - bitmap.Set(bits[i]); \ + bitmap.Set(bits[i]); \ } -#define CHECK_BITMAP(bitmap, bits) \ - { \ - size_t cur = 0, end = sizeof(bits) / sizeof(size_t); \ - for (size_t i = 0; i < bitmap.Size(); ++i) { \ - if (cur < end && bits[cur] == i) { \ - UNIT_ASSERT_EQUAL_C(bitmap.Get(i), true, "pos=" << i); \ - ++cur; \ - } else { \ +#define CHECK_BITMAP(bitmap, bits) \ + { \ + size_t cur = 0, end = sizeof(bits) / sizeof(size_t); \ + for (size_t i = 0; i < bitmap.Size(); ++i) { \ + if (cur < end && bits[cur] == i) { \ + UNIT_ASSERT_EQUAL_C(bitmap.Get(i), true, "pos=" << i); \ + ++cur; \ + } else { \ UNIT_ASSERT_EQUAL_C(bitmap.Get(i), false, "pos=" << i); \ - } \ - } \ + } \ + } \ } -#define CHECK_BITMAP_WITH_TAIL(bitmap, bits) \ - { \ - size_t cur = 0, end = sizeof(bits) / sizeof(size_t); \ - for (size_t i = 0; i < bitmap.Size(); ++i) { \ - if (cur < end) { \ - if (bits[cur] == i) { \ - UNIT_ASSERT_EQUAL_C(bitmap.Get(i), true, "pos=" << i); \ - ++cur; \ - } else { \ +#define CHECK_BITMAP_WITH_TAIL(bitmap, bits) \ + { \ + size_t cur = 0, end = sizeof(bits) / sizeof(size_t); \ + for (size_t i = 0; i < bitmap.Size(); ++i) { \ + if (cur < end) { \ + if (bits[cur] == i) { \ + UNIT_ASSERT_EQUAL_C(bitmap.Get(i), true, "pos=" << i); \ + ++cur; \ + } else { \ UNIT_ASSERT_EQUAL_C(bitmap.Get(i), false, "pos=" << i); \ - } \ - } else { \ - UNIT_ASSERT_EQUAL_C(bitmap.Get(i), true, "pos=" << i); \ - } \ - } \ + } \ + } else { \ + UNIT_ASSERT_EQUAL_C(bitmap.Get(i), true, "pos=" << i); \ + } \ + } \ } Y_UNIT_TEST_SUITE(TBitMapTest) { Y_UNIT_TEST(TestBitMap) { - TBitMap<101> bitmap; + TBitMap<101> bitmap; - UNIT_ASSERT_EQUAL(bitmap.Size(), 101); + UNIT_ASSERT_EQUAL(bitmap.Size(), 101); UNIT_ASSERT_EQUAL(bitmap.Count(), 0); UNIT_ASSERT_EQUAL(bitmap.FirstNonZeroBit(), 101); @@ -53,9 +53,9 @@ Y_UNIT_TEST_SUITE(TBitMapTest) { size_t setBits[] = {0, 50, 100}; CHECK_BITMAP(bitmap, setBits); - for (size_t i = 0; i < bitmap.Size(); ++i) { + for (size_t i = 0; i < bitmap.Size(); ++i) { UNIT_ASSERT_EQUAL(bitmap.Get(i), bitmap.Test(i)); - } + } UNIT_ASSERT_EQUAL(bitmap.Count(), 3); @@ -86,9 +86,9 @@ Y_UNIT_TEST_SUITE(TBitMapTest) { size_t setBits[] = {0, 50, 100}; CHECK_BITMAP(bitmap, setBits); - for (size_t i = 0; i < bitmap.Size(); ++i) { + for (size_t i = 0; i < bitmap.Size(); ++i) { UNIT_ASSERT_EQUAL(bitmap.Get(i), bitmap.Test(i)); - } + } UNIT_ASSERT_EQUAL(bitmap.Count(), 3); @@ -125,7 +125,7 @@ Y_UNIT_TEST_SUITE(TBitMapTest) { } Y_UNIT_TEST(TestAndFixed) { - TestAndImpl<TBitMap<101>>(); + TestAndImpl<TBitMap<101>>(); } Y_UNIT_TEST(TestAndDyn) { @@ -166,7 +166,7 @@ Y_UNIT_TEST_SUITE(TBitMapTest) { } Y_UNIT_TEST(TestOrFixed) { - TestOrImpl<TBitMap<145>>(); + TestOrImpl<TBitMap<145>>(); } Y_UNIT_TEST(TestOrDyn) { @@ -262,7 +262,7 @@ Y_UNIT_TEST_SUITE(TBitMapTest) { bitmap3.Clear(); INIT_BITMAP(bitmap3, initBits1); - TDynBitMap bitmap4 = ~((bitmap3 | 3) & bitmap2); + TDynBitMap bitmap4 = ~((bitmap3 | 3) & bitmap2); CHECK_BITMAP_WITH_TAIL(bitmap4, resBits); TBitMap<128, ui32> expmap; @@ -272,18 +272,18 @@ Y_UNIT_TEST_SUITE(TBitMapTest) { ui32 tst2 = 0; ui16 tst3 = 0; expmap.Export(32, tst1); - UNIT_ASSERT_EQUAL(tst1, (1 << 15) | (((ui64)1) << 58)); + UNIT_ASSERT_EQUAL(tst1, (1 << 15) | (((ui64)1) << 58)); expmap.Export(32, tst2); - UNIT_ASSERT_EQUAL(tst2, (1 << 15)); + UNIT_ASSERT_EQUAL(tst2, (1 << 15)); expmap.Export(32, tst3); - UNIT_ASSERT_EQUAL(tst3, (1 << 15)); + UNIT_ASSERT_EQUAL(tst3, (1 << 15)); expmap.Export(33, tst1); - UNIT_ASSERT_EQUAL(tst1, (1 << 14) | (((ui64)1) << 57)); + UNIT_ASSERT_EQUAL(tst1, (1 << 14) | (((ui64)1) << 57)); expmap.Export(33, tst2); - UNIT_ASSERT_EQUAL(tst2, (1 << 14)); + UNIT_ASSERT_EQUAL(tst2, (1 << 14)); expmap.Export(33, tst3); - UNIT_ASSERT_EQUAL(tst3, (1 << 14)); + UNIT_ASSERT_EQUAL(tst3, (1 << 14)); } Y_UNIT_TEST(TestShiftFixed) { diff --git a/util/generic/bitops.cpp b/util/generic/bitops.cpp index ebc56a7a80..db5667a21f 100644 --- a/util/generic/bitops.cpp +++ b/util/generic/bitops.cpp @@ -1,4 +1,4 @@ -#include "bitops.h" +#include "bitops.h" namespace NBitOps { namespace NPrivate { @@ -137,5 +137,5 @@ namespace NBitOps { ~0x7FFFFFFFFFFFFFFFULL, ~0xFFFFFFFFFFFFFFFFULL, }; - } -} + } +} diff --git a/util/generic/bitops.h b/util/generic/bitops.h index b8de09073b..2db15fc59b 100644 --- a/util/generic/bitops.h +++ b/util/generic/bitops.h @@ -1,33 +1,33 @@ #pragma once - -#include "ylimits.h" + +#include "ylimits.h" #include "typelist.h" - + #include <util/system/compiler.h> #include <util/system/yassert.h> - + #ifdef _MSC_VER - #include <intrin.h> + #include <intrin.h> #endif namespace NBitOps { - namespace NPrivate { + namespace NPrivate { template <unsigned N, typename T> - struct TClp2Helper { + struct TClp2Helper { static Y_FORCE_INLINE T Calc(T t) noexcept { - const T prev = TClp2Helper<N / 2, T>::Calc(t); - - return prev | (prev >> N); - } - }; - + const T prev = TClp2Helper<N / 2, T>::Calc(t); + + return prev | (prev >> N); + } + }; + template <typename T> - struct TClp2Helper<0u, T> { + struct TClp2Helper<0u, T> { static Y_FORCE_INLINE T Calc(T t) noexcept { - return t - 1; - } - }; - + return t - 1; + } + }; + extern const ui64 WORD_MASK[]; extern const ui64 INVERSE_WORD_MASK[]; @@ -67,7 +67,7 @@ namespace NBitOps { Y_ASSERT(value); // because __builtin_clz* have undefined result for zero. return std::numeric_limits<unsigned long>::digits - __builtin_clzl(value); } - + inline unsigned GetValueBitCountImpl(unsigned long long value) noexcept { Y_ASSERT(value); // because __builtin_clz* have undefined result for zero. return std::numeric_limits<unsigned long long>::digits - __builtin_clzll(value); @@ -87,7 +87,7 @@ namespace NBitOps { return result; } #endif - + #if defined(__GNUC__) inline unsigned CountTrailingZeroBitsImpl(unsigned int value) noexcept { Y_ASSERT(value); // because __builtin_ctz* have undefined result for zero. @@ -181,7 +181,7 @@ namespace NBitOps { return value; } - #if defined(_x86_64_) + #if defined(_x86_64_) Y_FORCE_INLINE ui64 RotateBitsRightImpl(ui64 value, ui8 shift) noexcept { __asm__("rorq %%cl, %0" : "=r"(value) @@ -195,17 +195,17 @@ namespace NBitOps { : "0"(value), "c"(shift)); return value; } - #endif + #endif #endif - } -} + } +} /** * Computes the next power of 2 higher or equal to the integer parameter `t`. * If `t` is a power of 2 will return `t`. * Result is undefined for `t == 0`. */ -template <typename T> +template <typename T> static inline T FastClp2(T t) noexcept { Y_ASSERT(t > 0); using TCvt = typename ::TUnsignedInts::template TSelectBy<TSizeOfPredicate<sizeof(T)>::template TResult>::type; @@ -219,17 +219,17 @@ template <typename T> Y_CONST_FUNCTION constexpr bool IsPowerOf2(T v) noexcept { return v > 0 && (v & (v - 1)) == 0; } - + /** * Returns the number of leading 0-bits in `value`, starting at the most significant bit position. */ -template <typename T> +template <typename T> static inline unsigned GetValueBitCount(T value) noexcept { Y_ASSERT(value > 0); using TCvt = typename ::TUnsignedInts::template TSelectBy<TSizeOfPredicate<sizeof(T)>::template TResult>::type; return ::NBitOps::NPrivate::GetValueBitCountImpl(static_cast<TCvt>(value)); -} - +} + /** * Returns the number of trailing 0-bits in `value`, starting at the least significant bit position */ @@ -238,7 +238,7 @@ static inline unsigned CountTrailingZeroBits(T value) noexcept { Y_ASSERT(value > 0); using TCvt = typename ::TUnsignedInts::template TSelectBy<TSizeOfPredicate<sizeof(T)>::template TResult>::type; return ::NBitOps::NPrivate::CountTrailingZeroBitsImpl(static_cast<TCvt>(value)); -} +} /* * Returns 64-bit mask with `bits` lower bits set. @@ -377,7 +377,7 @@ Y_FORCE_INLINE ui64 ReverseBits(ui64 t) { */ template <typename T> Y_FORCE_INLINE T ReverseBits(T v, ui64 bits) { - return bits ? (T(v & ::InverseMaskLowerBits(bits)) | T(ReverseBits(T(v & ::MaskLowerBits(bits)))) >> ((ui64{sizeof(T)} << ui64{3}) - bits)) : v; + return bits ? (T(v & ::InverseMaskLowerBits(bits)) | T(ReverseBits(T(v & ::MaskLowerBits(bits)))) >> ((ui64{sizeof(T)} << ui64{3}) - bits)) : v; } /* @@ -428,7 +428,7 @@ constexpr T RotateBitsRightCT(T value, const ui8 shift) noexcept { /* Remain `size` bits to current `offset` of `value` size, offset are less than number of bits in size_type */ -template <size_t Offset, size_t Size, class T> +template <size_t Offset, size_t Size, class T> Y_FORCE_INLINE T SelectBits(T value) { static_assert(Size < sizeof(T) * 8, "violated: Size < sizeof(T) * 8"); static_assert(Offset < sizeof(T) * 8, "violated: Offset < sizeof(T) * 8"); @@ -439,7 +439,7 @@ Y_FORCE_INLINE T SelectBits(T value) { /* Set `size` bits of `bits` to current offset of `value`. Requires that bits <= (1 << size) - 1 size, offset are less than number of bits in size_type */ -template <size_t Offset, size_t Size, class T> +template <size_t Offset, size_t Size, class T> void SetBits(T& value, T bits) { static_assert(Size < sizeof(T) * 8, "violated: Size < sizeof(T) * 8"); static_assert(Offset < sizeof(T) * 8, "violated: Offset < sizeof(T) * 8"); diff --git a/util/generic/bitops_ut.cpp b/util/generic/bitops_ut.cpp index 2b3f2fa6cb..d23c2b5c27 100644 --- a/util/generic/bitops_ut.cpp +++ b/util/generic/bitops_ut.cpp @@ -2,15 +2,15 @@ #include <library/cpp/testing/unittest/registar.h> -#include <util/string/builder.h> - +#include <util/string/builder.h> + template <typename T> static void TestCTZ() { for (unsigned int i = 0; i < (sizeof(T) << 3); ++i) { UNIT_ASSERT_VALUES_EQUAL(CountTrailingZeroBits(T(1) << i), i); } } - + template <typename T> static void TestFastClp2ForEachPowerOf2() { for (size_t i = 0; i < sizeof(T) * 8 - 1; ++i) { @@ -43,306 +43,306 @@ static T ReverseBitsSlow(T v) { return r; } -// DO_NOT_STYLE -Y_UNIT_TEST_SUITE(TBitOpsTest) { - Y_UNIT_TEST(TestCountTrailingZeroBits) { +// DO_NOT_STYLE +Y_UNIT_TEST_SUITE(TBitOpsTest) { + Y_UNIT_TEST(TestCountTrailingZeroBits) { TestCTZ<unsigned int>(); - TestCTZ<unsigned long>(); - TestCTZ<unsigned long long>(); - } - - Y_UNIT_TEST(TestIsPowerOf2) { - UNIT_ASSERT(!IsPowerOf2(-2)); - UNIT_ASSERT(!IsPowerOf2(-1)); - UNIT_ASSERT(!IsPowerOf2(0)); - UNIT_ASSERT(IsPowerOf2(1)); - UNIT_ASSERT(IsPowerOf2(2)); - UNIT_ASSERT(!IsPowerOf2(3)); - UNIT_ASSERT(IsPowerOf2(4)); - UNIT_ASSERT(!IsPowerOf2(5)); - UNIT_ASSERT(IsPowerOf2(0x10000000u)); - UNIT_ASSERT(!IsPowerOf2(0x10000001u)); - UNIT_ASSERT(IsPowerOf2(0x1000000000000000ull)); - UNIT_ASSERT(!IsPowerOf2(0x1000000000000001ull)); - } - - Y_UNIT_TEST(TestFastClp2) { - TestFastClp2ForEachPowerOf2<unsigned>(); - TestFastClp2ForEachPowerOf2<unsigned long>(); - TestFastClp2ForEachPowerOf2<unsigned long long>(); - } - - Y_UNIT_TEST(TestMask) { - for (ui32 i = 0; i < 64; ++i) { - UNIT_ASSERT_VALUES_EQUAL(MaskLowerBits(i), (ui64{1} << i) - 1); - UNIT_ASSERT_VALUES_EQUAL(InverseMaskLowerBits(i), ~MaskLowerBits(i)); - UNIT_ASSERT_VALUES_EQUAL(MaskLowerBits(i, i / 2), (ui64{1} << i) - 1 << (i / 2)); - UNIT_ASSERT_VALUES_EQUAL(InverseMaskLowerBits(i, i / 2), ~MaskLowerBits(i, i / 2)); - } + TestCTZ<unsigned long>(); + TestCTZ<unsigned long long>(); } - Y_UNIT_TEST(TestMostSignificantBit) { - static_assert(MostSignificantBitCT(0) == 0, "."); - static_assert(MostSignificantBitCT(1) == 0, "."); - static_assert(MostSignificantBitCT(5) == 2, "."); + Y_UNIT_TEST(TestIsPowerOf2) { + UNIT_ASSERT(!IsPowerOf2(-2)); + UNIT_ASSERT(!IsPowerOf2(-1)); + UNIT_ASSERT(!IsPowerOf2(0)); + UNIT_ASSERT(IsPowerOf2(1)); + UNIT_ASSERT(IsPowerOf2(2)); + UNIT_ASSERT(!IsPowerOf2(3)); + UNIT_ASSERT(IsPowerOf2(4)); + UNIT_ASSERT(!IsPowerOf2(5)); + UNIT_ASSERT(IsPowerOf2(0x10000000u)); + UNIT_ASSERT(!IsPowerOf2(0x10000001u)); + UNIT_ASSERT(IsPowerOf2(0x1000000000000000ull)); + UNIT_ASSERT(!IsPowerOf2(0x1000000000000001ull)); + } - for (ui32 i = 0; i < 64; ++i) { - UNIT_ASSERT_VALUES_EQUAL(i, MostSignificantBit(ui64{1} << i)); - } + Y_UNIT_TEST(TestFastClp2) { + TestFastClp2ForEachPowerOf2<unsigned>(); + TestFastClp2ForEachPowerOf2<unsigned long>(); + TestFastClp2ForEachPowerOf2<unsigned long long>(); + } - for (ui32 i = 0; i < 63; ++i) { - UNIT_ASSERT_VALUES_EQUAL(i + 1, MostSignificantBit(ui64{3} << i)); - } + Y_UNIT_TEST(TestMask) { + for (ui32 i = 0; i < 64; ++i) { + UNIT_ASSERT_VALUES_EQUAL(MaskLowerBits(i), (ui64{1} << i) - 1); + UNIT_ASSERT_VALUES_EQUAL(InverseMaskLowerBits(i), ~MaskLowerBits(i)); + UNIT_ASSERT_VALUES_EQUAL(MaskLowerBits(i, i / 2), (ui64{1} << i) - 1 << (i / 2)); + UNIT_ASSERT_VALUES_EQUAL(InverseMaskLowerBits(i, i / 2), ~MaskLowerBits(i, i / 2)); + } } - Y_UNIT_TEST(TestLeastSignificantBit) { - for (ui32 i = 0; i < 64; ++i) { - UNIT_ASSERT_VALUES_EQUAL(i, LeastSignificantBit(ui64{1} << i)); - } + Y_UNIT_TEST(TestMostSignificantBit) { + static_assert(MostSignificantBitCT(0) == 0, "."); + static_assert(MostSignificantBitCT(1) == 0, "."); + static_assert(MostSignificantBitCT(5) == 2, "."); - for (ui32 i = 0; i < 63; ++i) { - UNIT_ASSERT_VALUES_EQUAL(i, LeastSignificantBit(ui64{3} << i)); - } + for (ui32 i = 0; i < 64; ++i) { + UNIT_ASSERT_VALUES_EQUAL(i, MostSignificantBit(ui64{1} << i)); + } - for (ui32 i = 0; i < 64; ++i) { - ui64 value = (ui64(-1)) << i; - UNIT_ASSERT_VALUES_EQUAL(i, LeastSignificantBit(value)); - } + for (ui32 i = 0; i < 63; ++i) { + UNIT_ASSERT_VALUES_EQUAL(i + 1, MostSignificantBit(ui64{3} << i)); + } } - Y_UNIT_TEST(TestCeilLog2) { - UNIT_ASSERT_VALUES_EQUAL(CeilLog2(ui64{1}), 1); + Y_UNIT_TEST(TestLeastSignificantBit) { + for (ui32 i = 0; i < 64; ++i) { + UNIT_ASSERT_VALUES_EQUAL(i, LeastSignificantBit(ui64{1} << i)); + } + + for (ui32 i = 0; i < 63; ++i) { + UNIT_ASSERT_VALUES_EQUAL(i, LeastSignificantBit(ui64{3} << i)); + } - for (ui32 i = 2; i < 64; ++i) { - UNIT_ASSERT_VALUES_EQUAL(CeilLog2(ui64{1} << i), i); - UNIT_ASSERT_VALUES_EQUAL(CeilLog2((ui64{1} << i) | ui64{1}), i + 1); - } + for (ui32 i = 0; i < 64; ++i) { + ui64 value = (ui64(-1)) << i; + UNIT_ASSERT_VALUES_EQUAL(i, LeastSignificantBit(value)); + } } - Y_UNIT_TEST(TestReverse) { - for (ui64 i = 0; i < 0x100; ++i) { - UNIT_ASSERT_VALUES_EQUAL(ReverseBits((ui8)i), ReverseBitsSlow((ui8)i)); - UNIT_ASSERT_VALUES_EQUAL(ReverseBits((ui16)i), ReverseBitsSlow((ui16)i)); - UNIT_ASSERT_VALUES_EQUAL(ReverseBits((ui32)i), ReverseBitsSlow((ui32)i)); - UNIT_ASSERT_VALUES_EQUAL(ReverseBits((ui64)i), ReverseBitsSlow((ui64)i)); - UNIT_ASSERT_VALUES_EQUAL(ReverseBits((ui16)~i), ReverseBitsSlow((ui16)~i)); - UNIT_ASSERT_VALUES_EQUAL(ReverseBits((ui32)~i), ReverseBitsSlow((ui32)~i)); - UNIT_ASSERT_VALUES_EQUAL(ReverseBits((ui64)~i), ReverseBitsSlow((ui64)~i)); - } - - ui32 v = 0xF0F0F0F0; // 11110000111100001111000011110000 - for (ui32 i = 0; i < 4; ++i) { - UNIT_ASSERT_VALUES_EQUAL(ReverseBits(v, i + 1), v); - UNIT_ASSERT_VALUES_EQUAL(ReverseBits(v, 4 + 2 * i, 4 - i), v); - } - - UNIT_ASSERT_VALUES_EQUAL(ReverseBits(v, 8), 0xF0F0F00Fu); - UNIT_ASSERT_VALUES_EQUAL(ReverseBits(v, 8, 4), 0xF0F0FF00u); - - for (ui32 i = 0; i < 0x10000; ++i) { - for (ui32 j = 0; j <= 32; ++j) { - UNIT_ASSERT_VALUES_EQUAL_C(i, ReverseBits(ReverseBits(i, j), j), (TString)(TStringBuilder() << i << " " << j)); - } + Y_UNIT_TEST(TestCeilLog2) { + UNIT_ASSERT_VALUES_EQUAL(CeilLog2(ui64{1}), 1); + + for (ui32 i = 2; i < 64; ++i) { + UNIT_ASSERT_VALUES_EQUAL(CeilLog2(ui64{1} << i), i); + UNIT_ASSERT_VALUES_EQUAL(CeilLog2((ui64{1} << i) | ui64{1}), i + 1); } } - Y_UNIT_TEST(TestRotateBitsLeft) { - static_assert(RotateBitsLeftCT<ui8>(0b00000000u, 0) == 0b00000000u, ""); - static_assert(RotateBitsLeftCT<ui8>(0b00000001u, 0) == 0b00000001u, ""); - static_assert(RotateBitsLeftCT<ui8>(0b10000000u, 0) == 0b10000000u, ""); - static_assert(RotateBitsLeftCT<ui8>(0b00000001u, 1) == 0b00000010u, ""); - static_assert(RotateBitsLeftCT<ui8>(0b10000000u, 1) == 0b00000001u, ""); - static_assert(RotateBitsLeftCT<ui8>(0b00000101u, 1) == 0b00001010u, ""); - static_assert(RotateBitsLeftCT<ui8>(0b10100000u, 1) == 0b01000001u, ""); - static_assert(RotateBitsLeftCT<ui8>(0b10000000u, 7) == 0b01000000u, ""); - - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b00000000u, 0), 0b00000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b00000001u, 0), 0b00000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b10000000u, 0), 0b10000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b00000001u, 1), 0b00000010u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b10000000u, 1), 0b00000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b00000101u, 1), 0b00001010u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b10100000u, 1), 0b01000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b10000000u, 7), 0b01000000u); - - static_assert(RotateBitsLeftCT<ui16>(0b0000000000000000u, 0) == 0b0000000000000000u, ""); - static_assert(RotateBitsLeftCT<ui16>(0b0000000000000001u, 0) == 0b0000000000000001u, ""); - static_assert(RotateBitsLeftCT<ui16>(0b1000000000000000u, 0) == 0b1000000000000000u, ""); - static_assert(RotateBitsLeftCT<ui16>(0b0000000000000001u, 1) == 0b0000000000000010u, ""); - static_assert(RotateBitsLeftCT<ui16>(0b1000000000000000u, 1) == 0b0000000000000001u, ""); - static_assert(RotateBitsLeftCT<ui16>(0b0000000000000101u, 1) == 0b0000000000001010u, ""); - static_assert(RotateBitsLeftCT<ui16>(0b1010000000000000u, 1) == 0b0100000000000001u, ""); - static_assert(RotateBitsLeftCT<ui16>(0b1000000000000000u, 15) == 0b0100000000000000u, ""); - - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b0000000000000000u, 0), 0b0000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b0000000000000001u, 0), 0b0000000000000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b1000000000000000u, 0), 0b1000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b0000000000000001u, 1), 0b0000000000000010u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b1000000000000000u, 1), 0b0000000000000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b0000000000000101u, 1), 0b0000000000001010u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b1010000000000000u, 1), 0b0100000000000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b1000000000000000u, 15), 0b0100000000000000u); - - static_assert(RotateBitsLeftCT<ui32>(0b00000000000000000000000000000000u, 0) == 0b00000000000000000000000000000000u, ""); - static_assert(RotateBitsLeftCT<ui32>(0b00000000000000000000000000000001u, 0) == 0b00000000000000000000000000000001u, ""); - static_assert(RotateBitsLeftCT<ui32>(0b10000000000000000000000000000000u, 0) == 0b10000000000000000000000000000000u, ""); - static_assert(RotateBitsLeftCT<ui32>(0b00000000000000000000000000000001u, 1) == 0b00000000000000000000000000000010u, ""); - static_assert(RotateBitsLeftCT<ui32>(0b10000000000000000000000000000000u, 1) == 0b00000000000000000000000000000001u, ""); - static_assert(RotateBitsLeftCT<ui32>(0b00000000000000000000000000000101u, 1) == 0b00000000000000000000000000001010u, ""); - static_assert(RotateBitsLeftCT<ui32>(0b10100000000000000000000000000000u, 1) == 0b01000000000000000000000000000001u, ""); - static_assert(RotateBitsLeftCT<ui32>(0b10000000000000000000000000000000u, 31) == 0b01000000000000000000000000000000u, ""); - - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b00000000000000000000000000000000u, 0), 0b00000000000000000000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b00000000000000000000000000000001u, 0), 0b00000000000000000000000000000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b10000000000000000000000000000000u, 0), 0b10000000000000000000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b00000000000000000000000000000001u, 1), 0b00000000000000000000000000000010u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b10000000000000000000000000000000u, 1), 0b00000000000000000000000000000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b00000000000000000000000000000101u, 1), 0b00000000000000000000000000001010u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b10100000000000000000000000000000u, 1), 0b01000000000000000000000000000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b10000000000000000000000000000000u, 31), 0b01000000000000000000000000000000u); - - static_assert(RotateBitsLeftCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000000u, 0) == 0b0000000000000000000000000000000000000000000000000000000000000000u, ""); - static_assert(RotateBitsLeftCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 0) == 0b0000000000000000000000000000000000000000000000000000000000000001u, ""); - static_assert(RotateBitsLeftCT<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 0) == 0b1000000000000000000000000000000000000000000000000000000000000000u, ""); - static_assert(RotateBitsLeftCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 1) == 0b0000000000000000000000000000000000000000000000000000000000000010u, ""); - static_assert(RotateBitsLeftCT<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 1) == 0b0000000000000000000000000000000000000000000000000000000000000001u, ""); - static_assert(RotateBitsLeftCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000101u, 1) == 0b0000000000000000000000000000000000000000000000000000000000001010u, ""); - static_assert(RotateBitsLeftCT<ui64>(0b1010000000000000000000000000000000000000000000000000000000000000u, 1) == 0b0100000000000000000000000000000000000000000000000000000000000001u, ""); - static_assert(RotateBitsLeftCT<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 63) == 0b0100000000000000000000000000000000000000000000000000000000000000u, ""); - - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b0000000000000000000000000000000000000000000000000000000000000000u, 0), 0b0000000000000000000000000000000000000000000000000000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 0), 0b0000000000000000000000000000000000000000000000000000000000000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 0), 0b1000000000000000000000000000000000000000000000000000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 1), 0b0000000000000000000000000000000000000000000000000000000000000010u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 1), 0b0000000000000000000000000000000000000000000000000000000000000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b0000000000000000000000000000000000000000000000000000000000000101u, 1), 0b0000000000000000000000000000000000000000000000000000000000001010u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b1010000000000000000000000000000000000000000000000000000000000000u, 1), 0b0100000000000000000000000000000000000000000000000000000000000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 63), 0b0100000000000000000000000000000000000000000000000000000000000000u); - } - - Y_UNIT_TEST(TestRotateBitsRight) { - static_assert(RotateBitsRightCT<ui8>(0b00000000u, 0) == 0b00000000u, ""); - static_assert(RotateBitsRightCT<ui8>(0b00000001u, 0) == 0b00000001u, ""); - static_assert(RotateBitsRightCT<ui8>(0b10000000u, 0) == 0b10000000u, ""); - static_assert(RotateBitsRightCT<ui8>(0b00000001u, 1) == 0b10000000u, ""); - static_assert(RotateBitsRightCT<ui8>(0b10000000u, 1) == 0b01000000u, ""); - static_assert(RotateBitsRightCT<ui8>(0b00000101u, 1) == 0b10000010u, ""); - static_assert(RotateBitsRightCT<ui8>(0b10100000u, 1) == 0b01010000u, ""); - static_assert(RotateBitsRightCT<ui8>(0b00000001u, 7) == 0b00000010u, ""); - - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b00000000u, 0), 0b00000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b00000001u, 0), 0b00000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b10000000u, 0), 0b10000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b00000001u, 1), 0b10000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b10000000u, 1), 0b01000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b00000101u, 1), 0b10000010u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b10100000u, 1), 0b01010000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b00000001u, 7), 0b00000010u); - - static_assert(RotateBitsRightCT<ui16>(0b0000000000000000u, 0) == 0b0000000000000000u, ""); - static_assert(RotateBitsRightCT<ui16>(0b0000000000000001u, 0) == 0b0000000000000001u, ""); - static_assert(RotateBitsRightCT<ui16>(0b1000000000000000u, 0) == 0b1000000000000000u, ""); - static_assert(RotateBitsRightCT<ui16>(0b0000000000000001u, 1) == 0b1000000000000000u, ""); - static_assert(RotateBitsRightCT<ui16>(0b1000000000000000u, 1) == 0b0100000000000000u, ""); - static_assert(RotateBitsRightCT<ui16>(0b0000000000000101u, 1) == 0b1000000000000010u, ""); - static_assert(RotateBitsRightCT<ui16>(0b1010000000000000u, 1) == 0b0101000000000000u, ""); - static_assert(RotateBitsRightCT<ui16>(0b0000000000000001u, 15) == 0b0000000000000010u, ""); - - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b0000000000000000u, 0), 0b0000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b0000000000000001u, 0), 0b0000000000000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b1000000000000000u, 0), 0b1000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b0000000000000001u, 1), 0b1000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b1000000000000000u, 1), 0b0100000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b0000000000000101u, 1), 0b1000000000000010u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b1010000000000000u, 1), 0b0101000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b0000000000000001u, 15), 0b0000000000000010u); - - static_assert(RotateBitsRightCT<ui32>(0b00000000000000000000000000000000u, 0) == 0b00000000000000000000000000000000u, ""); - static_assert(RotateBitsRightCT<ui32>(0b00000000000000000000000000000001u, 0) == 0b00000000000000000000000000000001u, ""); - static_assert(RotateBitsRightCT<ui32>(0b10000000000000000000000000000000u, 0) == 0b10000000000000000000000000000000u, ""); - static_assert(RotateBitsRightCT<ui32>(0b00000000000000000000000000000001u, 1) == 0b10000000000000000000000000000000u, ""); - static_assert(RotateBitsRightCT<ui32>(0b10000000000000000000000000000000u, 1) == 0b01000000000000000000000000000000u, ""); - static_assert(RotateBitsRightCT<ui32>(0b00000000000000000000000000000101u, 1) == 0b10000000000000000000000000000010u, ""); - static_assert(RotateBitsRightCT<ui32>(0b10100000000000000000000000000000u, 1) == 0b01010000000000000000000000000000u, ""); - static_assert(RotateBitsRightCT<ui32>(0b00000000000000000000000000000001u, 31) == 0b00000000000000000000000000000010u, ""); - - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b00000000000000000000000000000000u, 0), 0b00000000000000000000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b00000000000000000000000000000001u, 0), 0b00000000000000000000000000000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b10000000000000000000000000000000u, 0), 0b10000000000000000000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b00000000000000000000000000000001u, 1), 0b10000000000000000000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b10000000000000000000000000000000u, 1), 0b01000000000000000000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b00000000000000000000000000000101u, 1), 0b10000000000000000000000000000010u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b10100000000000000000000000000000u, 1), 0b01010000000000000000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b00000000000000000000000000000001u, 31), 0b00000000000000000000000000000010u); - - static_assert(RotateBitsRightCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000000u, 0) == 0b0000000000000000000000000000000000000000000000000000000000000000u, ""); - static_assert(RotateBitsRightCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 0) == 0b0000000000000000000000000000000000000000000000000000000000000001u, ""); - static_assert(RotateBitsRightCT<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 0) == 0b1000000000000000000000000000000000000000000000000000000000000000u, ""); - static_assert(RotateBitsRightCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 1) == 0b1000000000000000000000000000000000000000000000000000000000000000u, ""); - static_assert(RotateBitsRightCT<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 1) == 0b0100000000000000000000000000000000000000000000000000000000000000u, ""); - static_assert(RotateBitsRightCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000101u, 1) == 0b1000000000000000000000000000000000000000000000000000000000000010u, ""); - static_assert(RotateBitsRightCT<ui64>(0b1010000000000000000000000000000000000000000000000000000000000000u, 1) == 0b0101000000000000000000000000000000000000000000000000000000000000u, ""); - static_assert(RotateBitsRightCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 63) == 0b0000000000000000000000000000000000000000000000000000000000000010u, ""); - - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b0000000000000000000000000000000000000000000000000000000000000000u, 0), 0b0000000000000000000000000000000000000000000000000000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 0), 0b0000000000000000000000000000000000000000000000000000000000000001u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 0), 0b1000000000000000000000000000000000000000000000000000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 1), 0b1000000000000000000000000000000000000000000000000000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 1), 0b0100000000000000000000000000000000000000000000000000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b0000000000000000000000000000000000000000000000000000000000000101u, 1), 0b1000000000000000000000000000000000000000000000000000000000000010u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b1010000000000000000000000000000000000000000000000000000000000000u, 1), 0b0101000000000000000000000000000000000000000000000000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 63), 0b0000000000000000000000000000000000000000000000000000000000000010u); - } - - Y_UNIT_TEST(TestSelectBits) { - ui8 firstui8Test = SelectBits<3, 4, ui8>(0b11111111u); - ui8 secondui8Test = SelectBits<2, 5, ui8>(0b11101101u); - UNIT_ASSERT_VALUES_EQUAL(firstui8Test, 0b00001111u); - UNIT_ASSERT_VALUES_EQUAL(secondui8Test, 0b00011011u); - - ui16 firstui16Test = SelectBits<9, 2, ui16>(0b1111111111111111u); - ui16 secondui16Test = SelectBits<3, 6, ui16>(0b1010011111010001u); - UNIT_ASSERT_VALUES_EQUAL(firstui16Test, 0b0000000000000011u); - UNIT_ASSERT_VALUES_EQUAL(secondui16Test, 0b0000000000111010u); - - ui32 firstui32Test = SelectBits<23, 31, ui32>(0b11111111111111111111111111111111u); - ui32 secondui32Test = SelectBits<0, 31, ui32>(0b10001011101010011111010000111111u); - UNIT_ASSERT_VALUES_EQUAL(firstui32Test, 0b00000000000000000000000111111111u); - UNIT_ASSERT_VALUES_EQUAL(secondui32Test, 0b00001011101010011111010000111111); - - ui64 firstui64Test = SelectBits<1, 62, ui64>(0b1111000000000000000000000000000000000000000000000000000000000000u); - ui64 secondui64Test = SelectBits<32, 43, ui64>(0b1111111111111111111111111111111111111111111111111111111111111111u); - UNIT_ASSERT_VALUES_EQUAL(firstui64Test, 0b0011100000000000000000000000000000000000000000000000000000000000u); - UNIT_ASSERT_VALUES_EQUAL(secondui64Test, 0b0000000000000000000000000000000011111111111111111111111111111111u); - } - - Y_UNIT_TEST(TestSetBits) { - ui8 firstui8Test = 0b11111111u; - SetBits<3, 4, ui8>(firstui8Test, 0b00001111u); - ui8 secondui8Test = 0b11101101u; - SetBits<2, 7, ui8>(secondui8Test, 0b01110111u); - UNIT_ASSERT_VALUES_EQUAL(firstui8Test, 0b11111111u); - UNIT_ASSERT_VALUES_EQUAL(secondui8Test, 0b11011101u); - - ui16 firstui16Test = 0b1111111111111111u; - SetBits<9, 4, ui16>(firstui16Test, 0b000000000000111u); - ui16 secondui16Test = 0b1010011111010001u; - SetBits<3, 15, ui16>(secondui16Test, 0b0010011111010001u); - UNIT_ASSERT_VALUES_EQUAL(firstui16Test, 0b1110111111111111u); - UNIT_ASSERT_VALUES_EQUAL(secondui16Test, 0b0011111010001001u); - - ui32 firstui32Test = 0b11111111111111111111111111111111u; - SetBits<23, 31, ui32>(firstui32Test, 0b01100001111111111001111101111111u); - ui32 secondui32Test = 0b10001011101010011111010000111111u; - SetBits<0, 31, ui32>(secondui32Test, 0b01111111111111111111111111111111u); - UNIT_ASSERT_VALUES_EQUAL(firstui32Test, 0b10111111111111111111111111111111u); - UNIT_ASSERT_VALUES_EQUAL(secondui32Test, 0b11111111111111111111111111111111u); - - ui64 firstui64Test = 0b1111000000000000000000000000000000000000000000000000000000000000u; - SetBits<1, 62, ui64>(firstui64Test, 0b0001000000000000000000000000000000000000000000000000000001010101u); - ui64 secondui64Test = 0b1111111111111111111111111111111111111111111111111111111111111111u; - SetBits<32, 43, ui64>(secondui64Test, 0b0000000000000000000000000000000000000111111111111111111111111111u); - UNIT_ASSERT_VALUES_EQUAL(firstui64Test, 0b1010000000000000000000000000000000000000000000000000000010101010u); - UNIT_ASSERT_VALUES_EQUAL(secondui64Test, 0b0000011111111111111111111111111111111111111111111111111111111111u); - } -}; + Y_UNIT_TEST(TestReverse) { + for (ui64 i = 0; i < 0x100; ++i) { + UNIT_ASSERT_VALUES_EQUAL(ReverseBits((ui8)i), ReverseBitsSlow((ui8)i)); + UNIT_ASSERT_VALUES_EQUAL(ReverseBits((ui16)i), ReverseBitsSlow((ui16)i)); + UNIT_ASSERT_VALUES_EQUAL(ReverseBits((ui32)i), ReverseBitsSlow((ui32)i)); + UNIT_ASSERT_VALUES_EQUAL(ReverseBits((ui64)i), ReverseBitsSlow((ui64)i)); + UNIT_ASSERT_VALUES_EQUAL(ReverseBits((ui16)~i), ReverseBitsSlow((ui16)~i)); + UNIT_ASSERT_VALUES_EQUAL(ReverseBits((ui32)~i), ReverseBitsSlow((ui32)~i)); + UNIT_ASSERT_VALUES_EQUAL(ReverseBits((ui64)~i), ReverseBitsSlow((ui64)~i)); + } + + ui32 v = 0xF0F0F0F0; // 11110000111100001111000011110000 + for (ui32 i = 0; i < 4; ++i) { + UNIT_ASSERT_VALUES_EQUAL(ReverseBits(v, i + 1), v); + UNIT_ASSERT_VALUES_EQUAL(ReverseBits(v, 4 + 2 * i, 4 - i), v); + } + + UNIT_ASSERT_VALUES_EQUAL(ReverseBits(v, 8), 0xF0F0F00Fu); + UNIT_ASSERT_VALUES_EQUAL(ReverseBits(v, 8, 4), 0xF0F0FF00u); + + for (ui32 i = 0; i < 0x10000; ++i) { + for (ui32 j = 0; j <= 32; ++j) { + UNIT_ASSERT_VALUES_EQUAL_C(i, ReverseBits(ReverseBits(i, j), j), (TString)(TStringBuilder() << i << " " << j)); + } + } + } + + Y_UNIT_TEST(TestRotateBitsLeft) { + static_assert(RotateBitsLeftCT<ui8>(0b00000000u, 0) == 0b00000000u, ""); + static_assert(RotateBitsLeftCT<ui8>(0b00000001u, 0) == 0b00000001u, ""); + static_assert(RotateBitsLeftCT<ui8>(0b10000000u, 0) == 0b10000000u, ""); + static_assert(RotateBitsLeftCT<ui8>(0b00000001u, 1) == 0b00000010u, ""); + static_assert(RotateBitsLeftCT<ui8>(0b10000000u, 1) == 0b00000001u, ""); + static_assert(RotateBitsLeftCT<ui8>(0b00000101u, 1) == 0b00001010u, ""); + static_assert(RotateBitsLeftCT<ui8>(0b10100000u, 1) == 0b01000001u, ""); + static_assert(RotateBitsLeftCT<ui8>(0b10000000u, 7) == 0b01000000u, ""); + + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b00000000u, 0), 0b00000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b00000001u, 0), 0b00000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b10000000u, 0), 0b10000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b00000001u, 1), 0b00000010u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b10000000u, 1), 0b00000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b00000101u, 1), 0b00001010u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b10100000u, 1), 0b01000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui8>(0b10000000u, 7), 0b01000000u); + + static_assert(RotateBitsLeftCT<ui16>(0b0000000000000000u, 0) == 0b0000000000000000u, ""); + static_assert(RotateBitsLeftCT<ui16>(0b0000000000000001u, 0) == 0b0000000000000001u, ""); + static_assert(RotateBitsLeftCT<ui16>(0b1000000000000000u, 0) == 0b1000000000000000u, ""); + static_assert(RotateBitsLeftCT<ui16>(0b0000000000000001u, 1) == 0b0000000000000010u, ""); + static_assert(RotateBitsLeftCT<ui16>(0b1000000000000000u, 1) == 0b0000000000000001u, ""); + static_assert(RotateBitsLeftCT<ui16>(0b0000000000000101u, 1) == 0b0000000000001010u, ""); + static_assert(RotateBitsLeftCT<ui16>(0b1010000000000000u, 1) == 0b0100000000000001u, ""); + static_assert(RotateBitsLeftCT<ui16>(0b1000000000000000u, 15) == 0b0100000000000000u, ""); + + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b0000000000000000u, 0), 0b0000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b0000000000000001u, 0), 0b0000000000000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b1000000000000000u, 0), 0b1000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b0000000000000001u, 1), 0b0000000000000010u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b1000000000000000u, 1), 0b0000000000000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b0000000000000101u, 1), 0b0000000000001010u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b1010000000000000u, 1), 0b0100000000000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui16>(0b1000000000000000u, 15), 0b0100000000000000u); + + static_assert(RotateBitsLeftCT<ui32>(0b00000000000000000000000000000000u, 0) == 0b00000000000000000000000000000000u, ""); + static_assert(RotateBitsLeftCT<ui32>(0b00000000000000000000000000000001u, 0) == 0b00000000000000000000000000000001u, ""); + static_assert(RotateBitsLeftCT<ui32>(0b10000000000000000000000000000000u, 0) == 0b10000000000000000000000000000000u, ""); + static_assert(RotateBitsLeftCT<ui32>(0b00000000000000000000000000000001u, 1) == 0b00000000000000000000000000000010u, ""); + static_assert(RotateBitsLeftCT<ui32>(0b10000000000000000000000000000000u, 1) == 0b00000000000000000000000000000001u, ""); + static_assert(RotateBitsLeftCT<ui32>(0b00000000000000000000000000000101u, 1) == 0b00000000000000000000000000001010u, ""); + static_assert(RotateBitsLeftCT<ui32>(0b10100000000000000000000000000000u, 1) == 0b01000000000000000000000000000001u, ""); + static_assert(RotateBitsLeftCT<ui32>(0b10000000000000000000000000000000u, 31) == 0b01000000000000000000000000000000u, ""); + + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b00000000000000000000000000000000u, 0), 0b00000000000000000000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b00000000000000000000000000000001u, 0), 0b00000000000000000000000000000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b10000000000000000000000000000000u, 0), 0b10000000000000000000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b00000000000000000000000000000001u, 1), 0b00000000000000000000000000000010u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b10000000000000000000000000000000u, 1), 0b00000000000000000000000000000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b00000000000000000000000000000101u, 1), 0b00000000000000000000000000001010u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b10100000000000000000000000000000u, 1), 0b01000000000000000000000000000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui32>(0b10000000000000000000000000000000u, 31), 0b01000000000000000000000000000000u); + + static_assert(RotateBitsLeftCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000000u, 0) == 0b0000000000000000000000000000000000000000000000000000000000000000u, ""); + static_assert(RotateBitsLeftCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 0) == 0b0000000000000000000000000000000000000000000000000000000000000001u, ""); + static_assert(RotateBitsLeftCT<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 0) == 0b1000000000000000000000000000000000000000000000000000000000000000u, ""); + static_assert(RotateBitsLeftCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 1) == 0b0000000000000000000000000000000000000000000000000000000000000010u, ""); + static_assert(RotateBitsLeftCT<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 1) == 0b0000000000000000000000000000000000000000000000000000000000000001u, ""); + static_assert(RotateBitsLeftCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000101u, 1) == 0b0000000000000000000000000000000000000000000000000000000000001010u, ""); + static_assert(RotateBitsLeftCT<ui64>(0b1010000000000000000000000000000000000000000000000000000000000000u, 1) == 0b0100000000000000000000000000000000000000000000000000000000000001u, ""); + static_assert(RotateBitsLeftCT<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 63) == 0b0100000000000000000000000000000000000000000000000000000000000000u, ""); + + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b0000000000000000000000000000000000000000000000000000000000000000u, 0), 0b0000000000000000000000000000000000000000000000000000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 0), 0b0000000000000000000000000000000000000000000000000000000000000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 0), 0b1000000000000000000000000000000000000000000000000000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 1), 0b0000000000000000000000000000000000000000000000000000000000000010u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 1), 0b0000000000000000000000000000000000000000000000000000000000000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b0000000000000000000000000000000000000000000000000000000000000101u, 1), 0b0000000000000000000000000000000000000000000000000000000000001010u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b1010000000000000000000000000000000000000000000000000000000000000u, 1), 0b0100000000000000000000000000000000000000000000000000000000000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsLeft<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 63), 0b0100000000000000000000000000000000000000000000000000000000000000u); + } + + Y_UNIT_TEST(TestRotateBitsRight) { + static_assert(RotateBitsRightCT<ui8>(0b00000000u, 0) == 0b00000000u, ""); + static_assert(RotateBitsRightCT<ui8>(0b00000001u, 0) == 0b00000001u, ""); + static_assert(RotateBitsRightCT<ui8>(0b10000000u, 0) == 0b10000000u, ""); + static_assert(RotateBitsRightCT<ui8>(0b00000001u, 1) == 0b10000000u, ""); + static_assert(RotateBitsRightCT<ui8>(0b10000000u, 1) == 0b01000000u, ""); + static_assert(RotateBitsRightCT<ui8>(0b00000101u, 1) == 0b10000010u, ""); + static_assert(RotateBitsRightCT<ui8>(0b10100000u, 1) == 0b01010000u, ""); + static_assert(RotateBitsRightCT<ui8>(0b00000001u, 7) == 0b00000010u, ""); + + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b00000000u, 0), 0b00000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b00000001u, 0), 0b00000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b10000000u, 0), 0b10000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b00000001u, 1), 0b10000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b10000000u, 1), 0b01000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b00000101u, 1), 0b10000010u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b10100000u, 1), 0b01010000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui8>(0b00000001u, 7), 0b00000010u); + + static_assert(RotateBitsRightCT<ui16>(0b0000000000000000u, 0) == 0b0000000000000000u, ""); + static_assert(RotateBitsRightCT<ui16>(0b0000000000000001u, 0) == 0b0000000000000001u, ""); + static_assert(RotateBitsRightCT<ui16>(0b1000000000000000u, 0) == 0b1000000000000000u, ""); + static_assert(RotateBitsRightCT<ui16>(0b0000000000000001u, 1) == 0b1000000000000000u, ""); + static_assert(RotateBitsRightCT<ui16>(0b1000000000000000u, 1) == 0b0100000000000000u, ""); + static_assert(RotateBitsRightCT<ui16>(0b0000000000000101u, 1) == 0b1000000000000010u, ""); + static_assert(RotateBitsRightCT<ui16>(0b1010000000000000u, 1) == 0b0101000000000000u, ""); + static_assert(RotateBitsRightCT<ui16>(0b0000000000000001u, 15) == 0b0000000000000010u, ""); + + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b0000000000000000u, 0), 0b0000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b0000000000000001u, 0), 0b0000000000000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b1000000000000000u, 0), 0b1000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b0000000000000001u, 1), 0b1000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b1000000000000000u, 1), 0b0100000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b0000000000000101u, 1), 0b1000000000000010u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b1010000000000000u, 1), 0b0101000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui16>(0b0000000000000001u, 15), 0b0000000000000010u); + + static_assert(RotateBitsRightCT<ui32>(0b00000000000000000000000000000000u, 0) == 0b00000000000000000000000000000000u, ""); + static_assert(RotateBitsRightCT<ui32>(0b00000000000000000000000000000001u, 0) == 0b00000000000000000000000000000001u, ""); + static_assert(RotateBitsRightCT<ui32>(0b10000000000000000000000000000000u, 0) == 0b10000000000000000000000000000000u, ""); + static_assert(RotateBitsRightCT<ui32>(0b00000000000000000000000000000001u, 1) == 0b10000000000000000000000000000000u, ""); + static_assert(RotateBitsRightCT<ui32>(0b10000000000000000000000000000000u, 1) == 0b01000000000000000000000000000000u, ""); + static_assert(RotateBitsRightCT<ui32>(0b00000000000000000000000000000101u, 1) == 0b10000000000000000000000000000010u, ""); + static_assert(RotateBitsRightCT<ui32>(0b10100000000000000000000000000000u, 1) == 0b01010000000000000000000000000000u, ""); + static_assert(RotateBitsRightCT<ui32>(0b00000000000000000000000000000001u, 31) == 0b00000000000000000000000000000010u, ""); + + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b00000000000000000000000000000000u, 0), 0b00000000000000000000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b00000000000000000000000000000001u, 0), 0b00000000000000000000000000000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b10000000000000000000000000000000u, 0), 0b10000000000000000000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b00000000000000000000000000000001u, 1), 0b10000000000000000000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b10000000000000000000000000000000u, 1), 0b01000000000000000000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b00000000000000000000000000000101u, 1), 0b10000000000000000000000000000010u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b10100000000000000000000000000000u, 1), 0b01010000000000000000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui32>(0b00000000000000000000000000000001u, 31), 0b00000000000000000000000000000010u); + + static_assert(RotateBitsRightCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000000u, 0) == 0b0000000000000000000000000000000000000000000000000000000000000000u, ""); + static_assert(RotateBitsRightCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 0) == 0b0000000000000000000000000000000000000000000000000000000000000001u, ""); + static_assert(RotateBitsRightCT<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 0) == 0b1000000000000000000000000000000000000000000000000000000000000000u, ""); + static_assert(RotateBitsRightCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 1) == 0b1000000000000000000000000000000000000000000000000000000000000000u, ""); + static_assert(RotateBitsRightCT<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 1) == 0b0100000000000000000000000000000000000000000000000000000000000000u, ""); + static_assert(RotateBitsRightCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000101u, 1) == 0b1000000000000000000000000000000000000000000000000000000000000010u, ""); + static_assert(RotateBitsRightCT<ui64>(0b1010000000000000000000000000000000000000000000000000000000000000u, 1) == 0b0101000000000000000000000000000000000000000000000000000000000000u, ""); + static_assert(RotateBitsRightCT<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 63) == 0b0000000000000000000000000000000000000000000000000000000000000010u, ""); + + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b0000000000000000000000000000000000000000000000000000000000000000u, 0), 0b0000000000000000000000000000000000000000000000000000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 0), 0b0000000000000000000000000000000000000000000000000000000000000001u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 0), 0b1000000000000000000000000000000000000000000000000000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 1), 0b1000000000000000000000000000000000000000000000000000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b1000000000000000000000000000000000000000000000000000000000000000u, 1), 0b0100000000000000000000000000000000000000000000000000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b0000000000000000000000000000000000000000000000000000000000000101u, 1), 0b1000000000000000000000000000000000000000000000000000000000000010u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b1010000000000000000000000000000000000000000000000000000000000000u, 1), 0b0101000000000000000000000000000000000000000000000000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(RotateBitsRight<ui64>(0b0000000000000000000000000000000000000000000000000000000000000001u, 63), 0b0000000000000000000000000000000000000000000000000000000000000010u); + } + + Y_UNIT_TEST(TestSelectBits) { + ui8 firstui8Test = SelectBits<3, 4, ui8>(0b11111111u); + ui8 secondui8Test = SelectBits<2, 5, ui8>(0b11101101u); + UNIT_ASSERT_VALUES_EQUAL(firstui8Test, 0b00001111u); + UNIT_ASSERT_VALUES_EQUAL(secondui8Test, 0b00011011u); + + ui16 firstui16Test = SelectBits<9, 2, ui16>(0b1111111111111111u); + ui16 secondui16Test = SelectBits<3, 6, ui16>(0b1010011111010001u); + UNIT_ASSERT_VALUES_EQUAL(firstui16Test, 0b0000000000000011u); + UNIT_ASSERT_VALUES_EQUAL(secondui16Test, 0b0000000000111010u); + + ui32 firstui32Test = SelectBits<23, 31, ui32>(0b11111111111111111111111111111111u); + ui32 secondui32Test = SelectBits<0, 31, ui32>(0b10001011101010011111010000111111u); + UNIT_ASSERT_VALUES_EQUAL(firstui32Test, 0b00000000000000000000000111111111u); + UNIT_ASSERT_VALUES_EQUAL(secondui32Test, 0b00001011101010011111010000111111); + + ui64 firstui64Test = SelectBits<1, 62, ui64>(0b1111000000000000000000000000000000000000000000000000000000000000u); + ui64 secondui64Test = SelectBits<32, 43, ui64>(0b1111111111111111111111111111111111111111111111111111111111111111u); + UNIT_ASSERT_VALUES_EQUAL(firstui64Test, 0b0011100000000000000000000000000000000000000000000000000000000000u); + UNIT_ASSERT_VALUES_EQUAL(secondui64Test, 0b0000000000000000000000000000000011111111111111111111111111111111u); + } + + Y_UNIT_TEST(TestSetBits) { + ui8 firstui8Test = 0b11111111u; + SetBits<3, 4, ui8>(firstui8Test, 0b00001111u); + ui8 secondui8Test = 0b11101101u; + SetBits<2, 7, ui8>(secondui8Test, 0b01110111u); + UNIT_ASSERT_VALUES_EQUAL(firstui8Test, 0b11111111u); + UNIT_ASSERT_VALUES_EQUAL(secondui8Test, 0b11011101u); + + ui16 firstui16Test = 0b1111111111111111u; + SetBits<9, 4, ui16>(firstui16Test, 0b000000000000111u); + ui16 secondui16Test = 0b1010011111010001u; + SetBits<3, 15, ui16>(secondui16Test, 0b0010011111010001u); + UNIT_ASSERT_VALUES_EQUAL(firstui16Test, 0b1110111111111111u); + UNIT_ASSERT_VALUES_EQUAL(secondui16Test, 0b0011111010001001u); + + ui32 firstui32Test = 0b11111111111111111111111111111111u; + SetBits<23, 31, ui32>(firstui32Test, 0b01100001111111111001111101111111u); + ui32 secondui32Test = 0b10001011101010011111010000111111u; + SetBits<0, 31, ui32>(secondui32Test, 0b01111111111111111111111111111111u); + UNIT_ASSERT_VALUES_EQUAL(firstui32Test, 0b10111111111111111111111111111111u); + UNIT_ASSERT_VALUES_EQUAL(secondui32Test, 0b11111111111111111111111111111111u); + + ui64 firstui64Test = 0b1111000000000000000000000000000000000000000000000000000000000000u; + SetBits<1, 62, ui64>(firstui64Test, 0b0001000000000000000000000000000000000000000000000000000001010101u); + ui64 secondui64Test = 0b1111111111111111111111111111111111111111111111111111111111111111u; + SetBits<32, 43, ui64>(secondui64Test, 0b0000000000000000000000000000000000000111111111111111111111111111u); + UNIT_ASSERT_VALUES_EQUAL(firstui64Test, 0b1010000000000000000000000000000000000000000000000000000010101010u); + UNIT_ASSERT_VALUES_EQUAL(secondui64Test, 0b0000011111111111111111111111111111111111111111111111111111111111u); + } +}; diff --git a/util/generic/bt_exception.cpp b/util/generic/bt_exception.cpp index bd59ba98f4..609870c4c0 100644 --- a/util/generic/bt_exception.cpp +++ b/util/generic/bt_exception.cpp @@ -1 +1 @@ -#include "bt_exception.h" +#include "bt_exception.h" diff --git a/util/generic/bt_exception.h b/util/generic/bt_exception.h index c4e770e021..018d2bc89a 100644 --- a/util/generic/bt_exception.h +++ b/util/generic/bt_exception.h @@ -1,24 +1,24 @@ -#pragma once - +#pragma once + #include <utility> -#include "yexception.h" - -#include <util/system/backtrace.h> - -template <class T> -class TWithBackTrace: public T { -public: - template <typename... Args> - inline TWithBackTrace(Args&&... args) +#include "yexception.h" + +#include <util/system/backtrace.h> + +template <class T> +class TWithBackTrace: public T { +public: + template <typename... Args> + inline TWithBackTrace(Args&&... args) : T(std::forward<Args>(args)...) - { - BT_.Capture(); - } - + { + BT_.Capture(); + } + const TBackTrace* BackTrace() const noexcept override { - return &BT_; - } - -private: - TBackTrace BT_; -}; + return &BT_; + } + +private: + TBackTrace BT_; +}; diff --git a/util/generic/buffer.cpp b/util/generic/buffer.cpp index 6289bdb3bd..b92697e1d0 100644 --- a/util/generic/buffer.cpp +++ b/util/generic/buffer.cpp @@ -2,26 +2,26 @@ #include "mem_copy.h" #include "string.h" #include "ymath.h" - -#include <util/system/sys_alloc.h> + +#include <util/system/sys_alloc.h> #include <util/system/sanitizers.h> - -TBuffer::TBuffer(size_t len) + +TBuffer::TBuffer(size_t len) : Data_(nullptr) - , Len_(0) - , Pos_(0) -{ - Reserve(len); -} - -TBuffer::TBuffer(TBuffer&& b) noexcept - : Data_(nullptr) - , Len_(0) - , Pos_(0) -{ - Swap(b); -} - + , Len_(0) + , Pos_(0) +{ + Reserve(len); +} + +TBuffer::TBuffer(TBuffer&& b) noexcept + : Data_(nullptr) + , Len_(0) + , Pos_(0) +{ + Swap(b); +} + TBuffer::TBuffer(const char* buf, size_t len) : Data_(nullptr) , Len_(0) @@ -30,7 +30,7 @@ TBuffer::TBuffer(const char* buf, size_t len) Append(buf, len); } -TBuffer& TBuffer::operator=(TBuffer&& b) noexcept { +TBuffer& TBuffer::operator=(TBuffer&& b) noexcept { y_deallocate(Data_); Data_ = b.Data_; @@ -72,28 +72,28 @@ void TBuffer::Fill(char ch, size_t len) { Y_ASSERT(Pos_ <= Len_); } -void TBuffer::DoReserve(size_t realLen) { +void TBuffer::DoReserve(size_t realLen) { // FastClp2<T>(x) returns 0 on x from [Max<T>/2 + 2, Max<T>] const size_t len = Max<size_t>(FastClp2(realLen), realLen); - + Y_ASSERT(realLen > Len_); Y_ASSERT(len >= realLen); - + Realloc(len); } void TBuffer::Realloc(size_t len) { Y_ASSERT(Pos_ <= len); - Data_ = (char*)y_reallocate(Data_, len); - Len_ = len; -} - + Data_ = (char*)y_reallocate(Data_, len); + Len_ = len; +} + TBuffer::~TBuffer() { - y_deallocate(Data_); -} - + y_deallocate(Data_); +} + void TBuffer::AsString(TString& s) { - s.assign(Data(), Size()); - Clear(); -} + s.assign(Data(), Size()); + Clear(); +} diff --git a/util/generic/buffer.h b/util/generic/buffer.h index 9c729b5225..9576467404 100644 --- a/util/generic/buffer.h +++ b/util/generic/buffer.h @@ -1,166 +1,166 @@ #pragma once - -#include "utility.h" - + +#include "utility.h" + #include <util/generic/fwd.h> -#include <util/system/align.h> -#include <util/system/yassert.h> - +#include <util/system/align.h> +#include <util/system/yassert.h> + #include <cstring> - + class TBuffer { -public: +public: using TIterator = char*; using TConstIterator = const char*; - - TBuffer(size_t len = 0); - TBuffer(const char* buf, size_t len); - - TBuffer(const TBuffer& b) - : Data_(nullptr) - , Len_(0) - , Pos_(0) - { - *this = b; - } - - TBuffer(TBuffer&& b) noexcept; - - TBuffer& operator=(TBuffer&& b) noexcept; - - TBuffer& operator=(const TBuffer& b) { + + TBuffer(size_t len = 0); + TBuffer(const char* buf, size_t len); + + TBuffer(const TBuffer& b) + : Data_(nullptr) + , Len_(0) + , Pos_(0) + { + *this = b; + } + + TBuffer(TBuffer&& b) noexcept; + + TBuffer& operator=(TBuffer&& b) noexcept; + + TBuffer& operator=(const TBuffer& b) { if (this != &b) { Assign(b.Data(), b.Size()); } - return *this; - } + return *this; + } ~TBuffer(); - + inline void Clear() noexcept { - Pos_ = 0; - } - + Pos_ = 0; + } + inline void EraseBack(size_t n) noexcept { Y_ASSERT(n <= Pos_); - Pos_ -= n; - } - + Pos_ -= n; + } + inline void Reset() noexcept { - TBuffer().Swap(*this); - } - - inline void Assign(const char* data, size_t len) { - Clear(); - Append(data, len); - } - - inline void Assign(const char* b, const char* e) { - Assign(b, e - b); - } - + TBuffer().Swap(*this); + } + + inline void Assign(const char* data, size_t len) { + Clear(); + Append(data, len); + } + + inline void Assign(const char* b, const char* e) { + Assign(b, e - b); + } + inline char* Data() noexcept { - return Data_; - } - + return Data_; + } + inline const char* Data() const noexcept { - return Data_; - } - + return Data_; + } + inline char* Pos() noexcept { - return Data_ + Pos_; - } + return Data_ + Pos_; + } inline const char* Pos() const noexcept { - return Data_ + Pos_; - } + return Data_ + Pos_; + } - /// Used space in bytes (do not mix with Capacity!) + /// Used space in bytes (do not mix with Capacity!) inline size_t Size() const noexcept { - return Pos_; - } - - Y_PURE_FUNCTION inline bool Empty() const noexcept { - return !Size(); - } - + return Pos_; + } + + Y_PURE_FUNCTION inline bool Empty() const noexcept { + return !Size(); + } + inline explicit operator bool() const noexcept { - return Size(); - } + return Size(); + } inline size_t Avail() const noexcept { - return Len_ - Pos_; - } - + return Len_ - Pos_; + } + void Append(const char* buf, size_t len); - - inline void Append(const char* b, const char* e) { - Append(b, e - b); - } - - inline void Append(char ch) { - if (Len_ == Pos_) { - Reserve(Len_ + 1); + + inline void Append(const char* b, const char* e) { + Append(b, e - b); + } + + inline void Append(char ch) { + if (Len_ == Pos_) { + Reserve(Len_ + 1); } - - *(Data() + Pos_++) = ch; - } - + + *(Data() + Pos_++) = ch; + } + void Fill(char ch, size_t len); - // Method is useful when first messages from buffer are processed, and - // the last message in buffer is incomplete, so we need to move partial - // message to the begin of the buffer and continue filling the buffer - // from the network. + // Method is useful when first messages from buffer are processed, and + // the last message in buffer is incomplete, so we need to move partial + // message to the begin of the buffer and continue filling the buffer + // from the network. inline void Chop(size_t pos, size_t count) { const auto end = pos + count; Y_ASSERT(end <= Pos_); - - if (count == 0) { - return; - } else if (count == Pos_) { - Pos_ = 0; - } else { + + if (count == 0) { + return; + } else if (count == Pos_) { + Pos_ = 0; + } else { memmove(Data_ + pos, Data_ + end, Pos_ - end); Pos_ -= count; } - } + } inline void ChopHead(size_t count) { Chop(0U, count); } - inline void Proceed(size_t pos) { + inline void Proceed(size_t pos) { //Y_ASSERT(pos <= Len_); // see discussion in REVIEW:29021 - Resize(pos); - } - - inline void Advance(size_t len) { + Resize(pos); + } + + inline void Advance(size_t len) { Resize(Pos_ + len); - } + } - inline void Reserve(size_t len) { - if (len > Len_) { - DoReserve(len); + inline void Reserve(size_t len) { + if (len > Len_) { + DoReserve(len); } - } - + } + inline void ReserveExactNeverCallMeInSaneCode(size_t len) { if (len > Len_) { Realloc(len); } } - inline void ShrinkToFit() { - if (Pos_ < Len_) { - Realloc(Pos_); + inline void ShrinkToFit() { + if (Pos_ < Len_) { + Realloc(Pos_); } - } + } - inline void Resize(size_t len) { - Reserve(len); - Pos_ = len; - } + inline void Resize(size_t len) { + Reserve(len); + Pos_ = len; + } // Method works like Resize, but allocates exact specified number of bytes // rather than rounded up to next power of 2 @@ -171,15 +171,15 @@ public: } inline size_t Capacity() const noexcept { - return Len_; - } - - inline void AlignUp(size_t align, char fillChar = '\0') { - size_t diff = ::AlignUp(Pos_, align) - Pos_; - while (diff-- > 0) { - Append(fillChar); - } - } + return Len_; + } + + inline void AlignUp(size_t align, char fillChar = '\0') { + size_t diff = ::AlignUp(Pos_, align) - Pos_; + while (diff-- > 0) { + Append(fillChar); + } + } inline char* data() noexcept { return Data(); @@ -194,35 +194,35 @@ public: } inline void Swap(TBuffer& r) noexcept { - DoSwap(Data_, r.Data_); - DoSwap(Len_, r.Len_); - DoSwap(Pos_, r.Pos_); - } - - /* - * after this call buffer becomes empty - */ + DoSwap(Data_, r.Data_); + DoSwap(Len_, r.Len_); + DoSwap(Pos_, r.Pos_); + } + + /* + * after this call buffer becomes empty + */ void AsString(TString& s); - - /* - * iterator-like interface - */ + + /* + * iterator-like interface + */ inline TIterator Begin() noexcept { - return Data(); - } - + return Data(); + } + inline TIterator End() noexcept { - return Begin() + Size(); - } - + return Begin() + Size(); + } + inline TConstIterator Begin() const noexcept { - return Data(); - } - + return Data(); + } + inline TConstIterator End() const noexcept { - return Begin() + Size(); - } - + return Begin() + Size(); + } + bool operator==(const TBuffer& other) const noexcept { if (Empty()) { return other.Empty(); @@ -234,12 +234,12 @@ public: return !(*this == other); } -private: - void DoReserve(size_t len); - void Realloc(size_t len); - -private: - char* Data_; - size_t Len_; - size_t Pos_; -}; +private: + void DoReserve(size_t len); + void Realloc(size_t len); + +private: + char* Data_; + size_t Len_; + size_t Pos_; +}; diff --git a/util/generic/buffer_ut.cpp b/util/generic/buffer_ut.cpp index 455a02e159..437d7122ec 100644 --- a/util/generic/buffer_ut.cpp +++ b/util/generic/buffer_ut.cpp @@ -1,28 +1,28 @@ #include <library/cpp/testing/unittest/registar.h> - -#include <util/system/datetime.h> + +#include <util/system/datetime.h> #include "string.h" -#include "vector.h" -#include "buffer.h" - +#include "vector.h" +#include "buffer.h" + Y_UNIT_TEST_SUITE(TBufferTest) { Y_UNIT_TEST(TestEraseBack) { - TBuffer buf; - - buf.Append("1234567", 7); - buf.Reserve(1000); - buf.Resize(6); - buf.EraseBack(2); - + TBuffer buf; + + buf.Append("1234567", 7); + buf.Reserve(1000); + buf.Resize(6); + buf.EraseBack(2); + UNIT_ASSERT_EQUAL(TString(buf.data(), buf.size()), "1234"); - } - + } + Y_UNIT_TEST(TestAppend) { const char data[] = "1234567890qwertyuiop"; - + TBuffer buf(13); TString str; - + for (size_t i = 0; i < 10; ++i) { for (size_t j = 0; j < sizeof(data) - 1; ++j) { buf.Append(data, j); @@ -31,14 +31,14 @@ Y_UNIT_TEST_SUITE(TBufferTest) { str.append('q'); } } - + UNIT_ASSERT_EQUAL(TString(buf.data(), buf.size()), str); - } - + } + Y_UNIT_TEST(TestReset) { char content[] = "some text"; TBuffer buf; - + buf.Append(content, sizeof(content)); buf.Clear(); @@ -146,37 +146,37 @@ Y_UNIT_TEST(TestAlignUp) { #if 0 Y_UNIT_TEST(TestSpeed) { - const char data[] = "1234567890qwertyuiop"; - const size_t c = 100000; - ui64 t1 = 0; - ui64 t2 = 0; - - { - TBuffer buf; - - t1 = MicroSeconds(); - - for (size_t i = 0; i < c; ++i) { - buf.Append(data, sizeof(data)); - } - - t1 = MicroSeconds() - t1; - } - - { + const char data[] = "1234567890qwertyuiop"; + const size_t c = 100000; + ui64 t1 = 0; + ui64 t2 = 0; + + { + TBuffer buf; + + t1 = MicroSeconds(); + + for (size_t i = 0; i < c; ++i) { + buf.Append(data, sizeof(data)); + } + + t1 = MicroSeconds() - t1; + } + + { TVector<char> buf; - - t2 = MicroSeconds(); - - for (size_t i = 0; i < c; ++i) { - buf.insert(buf.end(), data, data + sizeof(data)); - } - - t2 = MicroSeconds() - t2; - } - - UNIT_ASSERT(t1 < t2); -} + + t2 = MicroSeconds(); + + for (size_t i = 0; i < c; ++i) { + buf.insert(buf.end(), data, data + sizeof(data)); + } + + t2 = MicroSeconds() - t2; + } + + UNIT_ASSERT(t1 < t2); +} #endif Y_UNIT_TEST(TestFillAndChop) { @@ -202,4 +202,4 @@ Y_UNIT_TEST(TestSpeed) { UNIT_ASSERT(buf2 == buf1); } -} +} diff --git a/util/generic/cast.cpp b/util/generic/cast.cpp index 9e7380f2fe..11f82364d3 100644 --- a/util/generic/cast.cpp +++ b/util/generic/cast.cpp @@ -1 +1 @@ -#include "cast.h" +#include "cast.h" diff --git a/util/generic/cast.h b/util/generic/cast.h index dbc9b2b298..0d4a41f385 100644 --- a/util/generic/cast.h +++ b/util/generic/cast.h @@ -1,15 +1,15 @@ #pragma once - -#include "typetraits.h" + +#include "typetraits.h" #include "yexception.h" - -#include <util/system/compat.h> + +#include <util/system/compat.h> #include <util/system/type_name.h> #include <util/system/unaligned_mem.h> -#include <util/system/yassert.h> - +#include <util/system/yassert.h> + #include <cstdlib> - + template <class T, class F> static inline T VerifyDynamicCast(F f) { if (!f) { @@ -23,10 +23,10 @@ static inline T VerifyDynamicCast(F f) { return ret; } -#if !defined(NDEBUG) - #define USE_DEBUG_CHECKED_CAST -#endif - +#if !defined(NDEBUG) + #define USE_DEBUG_CHECKED_CAST +#endif + namespace NPrivate { template <typename T, typename F> static T DynamicCast(F f) { @@ -34,59 +34,59 @@ namespace NPrivate { } } -/* - * replacement for dynamic_cast(dynamic_cast in debug mode, else static_cast) - */ -template <class T, class F> -static inline T CheckedCast(F f) { -#if defined(USE_DEBUG_CHECKED_CAST) +/* + * replacement for dynamic_cast(dynamic_cast in debug mode, else static_cast) + */ +template <class T, class F> +static inline T CheckedCast(F f) { +#if defined(USE_DEBUG_CHECKED_CAST) return VerifyDynamicCast<T>(f); -#else - /* Make sure F is polymorphic. - * Without this cast, CheckedCast with non-polymorphic F - * incorrectly compiled without error in release mode. - */ - { - auto&& x = &::NPrivate::DynamicCast<T, F>; - - (void)x; - } - - return static_cast<T>(f); +#else + /* Make sure F is polymorphic. + * Without this cast, CheckedCast with non-polymorphic F + * incorrectly compiled without error in release mode. + */ + { + auto&& x = &::NPrivate::DynamicCast<T, F>; + + (void)x; + } + + return static_cast<T>(f); #endif // USE_DEBUG_CHECKED_CAST -} - -/* - * be polite - */ -#undef USE_DEBUG_CHECKED_CAST - -template <bool isUnsigned> -class TInteger; - -template <> -class TInteger<true> { -public: - template <class TUnsigned> +} + +/* + * be polite + */ +#undef USE_DEBUG_CHECKED_CAST + +template <bool isUnsigned> +class TInteger; + +template <> +class TInteger<true> { +public: + template <class TUnsigned> static constexpr bool IsNegative(TUnsigned) noexcept { - return false; - } -}; - -template <> -class TInteger<false> { -public: - template <class TSigned> + return false; + } +}; + +template <> +class TInteger<false> { +public: + template <class TSigned> static constexpr bool IsNegative(const TSigned value) noexcept { - return value < 0; - } -}; - -template <class TType> + return value < 0; + } +}; + +template <class TType> constexpr bool IsNegative(const TType value) noexcept { return TInteger<std::is_unsigned<TType>::value>::IsNegative(value); -} - +} + namespace NPrivate { template <class T> using TUnderlyingTypeOrSelf = typename std::conditional< @@ -106,8 +106,8 @@ namespace NPrivate { }; } -template <class TSmallInt, class TLargeInt> -constexpr std::enable_if_t<::NPrivate::TSafelyConvertible<TSmallInt, TLargeInt>::Result, TSmallInt> SafeIntegerCast(TLargeInt largeInt) noexcept { +template <class TSmallInt, class TLargeInt> +constexpr std::enable_if_t<::NPrivate::TSafelyConvertible<TSmallInt, TLargeInt>::Result, TSmallInt> SafeIntegerCast(TLargeInt largeInt) noexcept { return static_cast<TSmallInt>(largeInt); } @@ -125,22 +125,22 @@ inline std::enable_if_t<!::NPrivate::TSafelyConvertible<TSmall, TLarge>::Result, } TSmallInt smallInt = TSmallInt(largeInt); - + if (std::is_signed<TSmallInt>::value && std::is_unsigned<TLargeInt>::value) { if (IsNegative(smallInt)) { ythrow TBadCastException() << "Conversion '" << TypeName<TLarge>() << '{' << TLargeInt(largeInt) << "}' to '" << TypeName<TSmallInt>() << "', positive value converted to negative"; - } - } - + } + } + if (TLargeInt(smallInt) != largeInt) { ythrow TBadCastException() << "Conversion '" << TypeName<TLarge>() << '{' << TLargeInt(largeInt) << "}' to '" << TypeName<TSmallInt>() << "', loss of data"; - } - + } + return static_cast<TSmall>(smallInt); -} +} template <class TSmallInt, class TLargeInt> inline TSmallInt IntegerCast(TLargeInt largeInt) noexcept { diff --git a/util/generic/cast_ut.cpp b/util/generic/cast_ut.cpp index ff23f617da..718a8de79d 100644 --- a/util/generic/cast_ut.cpp +++ b/util/generic/cast_ut.cpp @@ -1,45 +1,45 @@ -#include "cast.h" - +#include "cast.h" + #include <library/cpp/testing/unittest/registar.h> - -class TGenericCastsTest: public TTestBase { - UNIT_TEST_SUITE(TGenericCastsTest); - UNIT_TEST(TestVerifyDynamicCast) - UNIT_TEST(TestIntegralCast) + +class TGenericCastsTest: public TTestBase { + UNIT_TEST_SUITE(TGenericCastsTest); + UNIT_TEST(TestVerifyDynamicCast) + UNIT_TEST(TestIntegralCast) UNIT_TEST(TestEnumCast) UNIT_TEST(TestToUnderlying) UNIT_TEST(TestBitCast) - UNIT_TEST_SUITE_END(); - -private: - struct TAaa { + UNIT_TEST_SUITE_END(); + +private: + struct TAaa { virtual ~TAaa() = default; - }; - struct TBbb: public TAaa {}; - - inline void TestVerifyDynamicCast() { - TBbb bbb; - TAaa* aaa = &bbb; - TAaa* aaa2 = VerifyDynamicCast<TBbb*>(aaa); - UNIT_ASSERT(aaa == aaa2); - } - - void TestIntegralCast() { - UNIT_ASSERT_EXCEPTION(SafeIntegerCast<ui32>(-5), TBadCastException); - UNIT_ASSERT_EXCEPTION(SafeIntegerCast<ui16>(static_cast<i32>(Max<ui16>() + 10)), TBadCastException); - UNIT_ASSERT_EXCEPTION(SafeIntegerCast<ui16>(static_cast<ui32>(Max<ui16>() + 10)), TBadCastException); - } + }; + struct TBbb: public TAaa {}; + + inline void TestVerifyDynamicCast() { + TBbb bbb; + TAaa* aaa = &bbb; + TAaa* aaa2 = VerifyDynamicCast<TBbb*>(aaa); + UNIT_ASSERT(aaa == aaa2); + } + + void TestIntegralCast() { + UNIT_ASSERT_EXCEPTION(SafeIntegerCast<ui32>(-5), TBadCastException); + UNIT_ASSERT_EXCEPTION(SafeIntegerCast<ui16>(static_cast<i32>(Max<ui16>() + 10)), TBadCastException); + UNIT_ASSERT_EXCEPTION(SafeIntegerCast<ui16>(static_cast<ui32>(Max<ui16>() + 10)), TBadCastException); + } inline void TestEnumCast() { enum A { AM1 = -1 }; - enum B: int { + enum B: int { BM1 = -1 }; - enum class C: unsigned short { + enum class C: unsigned short { CM1 = 1 }; @@ -61,11 +61,11 @@ private: AM1 = -1 }; - enum B: int { + enum B: int { BM1 = -1 }; - enum class C: unsigned short { + enum class C: unsigned short { CM1 = 1 }; @@ -107,6 +107,6 @@ private: UNIT_ASSERT_VALUES_EQUAL(structValue.d, 0x11); } } -}; - -UNIT_TEST_SUITE_REGISTRATION(TGenericCastsTest); +}; + +UNIT_TEST_SUITE_REGISTRATION(TGenericCastsTest); diff --git a/util/generic/deque.cpp b/util/generic/deque.cpp index 75dec05949..3c055780ab 100644 --- a/util/generic/deque.cpp +++ b/util/generic/deque.cpp @@ -1 +1 @@ -#include "deque.h" +#include "deque.h" diff --git a/util/generic/deque.h b/util/generic/deque.h index 457273e660..2dabaf3177 100644 --- a/util/generic/deque.h +++ b/util/generic/deque.h @@ -1,25 +1,25 @@ #pragma once - + #include "fwd.h" -#include <util/memory/alloc.h> - -#include <deque> +#include <util/memory/alloc.h> + +#include <deque> #include <memory> #include <initializer_list> - + template <class T, class A> class TDeque: public std::deque<T, TReboundAllocator<A, T>> { using TBase = std::deque<T, TReboundAllocator<A, T>>; - + public: using TBase::TBase; - + inline yssize_t ysize() const noexcept { return (yssize_t)this->size(); - } - - inline explicit operator bool() const noexcept { + } + + inline explicit operator bool() const noexcept { return !this->empty(); } -}; +}; diff --git a/util/generic/deque_ut.cpp b/util/generic/deque_ut.cpp index 3d1904e47e..93bf50fa92 100644 --- a/util/generic/deque_ut.cpp +++ b/util/generic/deque_ut.cpp @@ -1,31 +1,31 @@ -#include "deque.h" - +#include "deque.h" + #include <library/cpp/testing/unittest/registar.h> - + #include <utility> -#include "yexception.h" - -class TDequeTest: public TTestBase { - UNIT_TEST_SUITE(TDequeTest); - UNIT_TEST(TestConstructorsAndAssignments); - UNIT_TEST(TestDeque1); - UNIT_TEST(TestAt); - UNIT_TEST(TestInsert); - UNIT_TEST(TestErase); - UNIT_TEST(TestAutoRef); - UNIT_TEST_SUITE_END(); - -protected: - void TestConstructorsAndAssignments(); - void TestDeque1(); - void TestInsert(); - void TestErase(); - void TestAt(); - void TestAutoRef(); -}; - -UNIT_TEST_SUITE_REGISTRATION(TDequeTest); - +#include "yexception.h" + +class TDequeTest: public TTestBase { + UNIT_TEST_SUITE(TDequeTest); + UNIT_TEST(TestConstructorsAndAssignments); + UNIT_TEST(TestDeque1); + UNIT_TEST(TestAt); + UNIT_TEST(TestInsert); + UNIT_TEST(TestErase); + UNIT_TEST(TestAutoRef); + UNIT_TEST_SUITE_END(); + +protected: + void TestConstructorsAndAssignments(); + void TestDeque1(); + void TestInsert(); + void TestErase(); + void TestAt(); + void TestAutoRef(); +}; + +UNIT_TEST_SUITE_REGISTRATION(TDequeTest); + void TDequeTest::TestConstructorsAndAssignments() { using container = TDeque<int>; @@ -65,189 +65,189 @@ void TDequeTest::TestConstructorsAndAssignments() { UNIT_ASSERT_VALUES_EQUAL(c4, container(std::begin(array), std::end(array))); } -void TDequeTest::TestDeque1() { +void TDequeTest::TestDeque1() { TDeque<int> d; UNIT_ASSERT(!d); - d.push_back(4); - d.push_back(9); - d.push_back(16); - d.push_front(1); - + d.push_back(4); + d.push_back(9); + d.push_back(16); + d.push_front(1); + UNIT_ASSERT(d); - UNIT_ASSERT(d[0] == 1); - UNIT_ASSERT(d[1] == 4); - UNIT_ASSERT(d[2] == 9); - UNIT_ASSERT(d[3] == 16); - - d.pop_front(); - d[2] = 25; - - UNIT_ASSERT(d[0] == 4); - UNIT_ASSERT(d[1] == 9); - UNIT_ASSERT(d[2] == 25); - - //Some compile time tests: + UNIT_ASSERT(d[0] == 1); + UNIT_ASSERT(d[1] == 4); + UNIT_ASSERT(d[2] == 9); + UNIT_ASSERT(d[3] == 16); + + d.pop_front(); + d[2] = 25; + + UNIT_ASSERT(d[0] == 4); + UNIT_ASSERT(d[1] == 9); + UNIT_ASSERT(d[2] == 25); + + //Some compile time tests: TDeque<int>::iterator dit = d.begin(); TDeque<int>::const_iterator cdit(d.begin()); - - UNIT_ASSERT((dit - cdit) == 0); - UNIT_ASSERT((cdit - dit) == 0); - UNIT_ASSERT((dit - dit) == 0); - UNIT_ASSERT((cdit - cdit) == 0); - UNIT_ASSERT(!((dit < cdit) || (dit > cdit) || (dit != cdit) || !(dit <= cdit) || !(dit >= cdit))); -} - -void TDequeTest::TestInsert() { + + UNIT_ASSERT((dit - cdit) == 0); + UNIT_ASSERT((cdit - dit) == 0); + UNIT_ASSERT((dit - dit) == 0); + UNIT_ASSERT((cdit - cdit) == 0); + UNIT_ASSERT(!((dit < cdit) || (dit > cdit) || (dit != cdit) || !(dit <= cdit) || !(dit >= cdit))); +} + +void TDequeTest::TestInsert() { TDeque<int> d; - d.push_back(0); - d.push_back(1); - d.push_back(2); - - UNIT_ASSERT(d.size() == 3); - + d.push_back(0); + d.push_back(1); + d.push_back(2); + + UNIT_ASSERT(d.size() == 3); + TDeque<int>::iterator dit; - - //Insertion before begin: - dit = d.insert(d.begin(), 3); - UNIT_ASSERT(dit != d.end()); - UNIT_ASSERT(*dit == 3); - UNIT_ASSERT(d.size() == 4); - UNIT_ASSERT(d[0] == 3); - - //Insertion after begin: - dit = d.insert(d.begin() + 1, 4); - UNIT_ASSERT(dit != d.end()); - UNIT_ASSERT(*dit == 4); - UNIT_ASSERT(d.size() == 5); - UNIT_ASSERT(d[1] == 4); - - //Insertion at end: - dit = d.insert(d.end(), 5); - UNIT_ASSERT(dit != d.end()); - UNIT_ASSERT(*dit == 5); - UNIT_ASSERT(d.size() == 6); - UNIT_ASSERT(d[5] == 5); - - //Insertion before last element: - dit = d.insert(d.end() - 1, 6); - UNIT_ASSERT(dit != d.end()); - UNIT_ASSERT(*dit == 6); - UNIT_ASSERT(d.size() == 7); - UNIT_ASSERT(d[5] == 6); - - //Insertion of several elements before begin - d.insert(d.begin(), 2, 7); - UNIT_ASSERT(d.size() == 9); - UNIT_ASSERT(d[0] == 7); - UNIT_ASSERT(d[1] == 7); - - //Insertion of several elements after begin - //There is more elements to insert than elements before insertion position - d.insert(d.begin() + 1, 2, 8); - UNIT_ASSERT(d.size() == 11); - UNIT_ASSERT(d[1] == 8); - UNIT_ASSERT(d[2] == 8); - - //There is less elements to insert than elements before insertion position - d.insert(d.begin() + 3, 2, 9); - UNIT_ASSERT(d.size() == 13); - UNIT_ASSERT(d[3] == 9); - UNIT_ASSERT(d[4] == 9); - - //Insertion of several elements at end: - d.insert(d.end(), 2, 10); - UNIT_ASSERT(d.size() == 15); - UNIT_ASSERT(d[14] == 10); - UNIT_ASSERT(d[13] == 10); - - //Insertion of several elements before last: - //There is more elements to insert than elements after insertion position - d.insert(d.end() - 1, 2, 11); - UNIT_ASSERT(d.size() == 17); - UNIT_ASSERT(d[15] == 11); - UNIT_ASSERT(d[14] == 11); - - //There is less elements to insert than elements after insertion position - d.insert(d.end() - 3, 2, 12); - UNIT_ASSERT(d.size() == 19); - UNIT_ASSERT(d[15] == 12); - UNIT_ASSERT(d[14] == 12); -} - -void TDequeTest::TestAt() { + + //Insertion before begin: + dit = d.insert(d.begin(), 3); + UNIT_ASSERT(dit != d.end()); + UNIT_ASSERT(*dit == 3); + UNIT_ASSERT(d.size() == 4); + UNIT_ASSERT(d[0] == 3); + + //Insertion after begin: + dit = d.insert(d.begin() + 1, 4); + UNIT_ASSERT(dit != d.end()); + UNIT_ASSERT(*dit == 4); + UNIT_ASSERT(d.size() == 5); + UNIT_ASSERT(d[1] == 4); + + //Insertion at end: + dit = d.insert(d.end(), 5); + UNIT_ASSERT(dit != d.end()); + UNIT_ASSERT(*dit == 5); + UNIT_ASSERT(d.size() == 6); + UNIT_ASSERT(d[5] == 5); + + //Insertion before last element: + dit = d.insert(d.end() - 1, 6); + UNIT_ASSERT(dit != d.end()); + UNIT_ASSERT(*dit == 6); + UNIT_ASSERT(d.size() == 7); + UNIT_ASSERT(d[5] == 6); + + //Insertion of several elements before begin + d.insert(d.begin(), 2, 7); + UNIT_ASSERT(d.size() == 9); + UNIT_ASSERT(d[0] == 7); + UNIT_ASSERT(d[1] == 7); + + //Insertion of several elements after begin + //There is more elements to insert than elements before insertion position + d.insert(d.begin() + 1, 2, 8); + UNIT_ASSERT(d.size() == 11); + UNIT_ASSERT(d[1] == 8); + UNIT_ASSERT(d[2] == 8); + + //There is less elements to insert than elements before insertion position + d.insert(d.begin() + 3, 2, 9); + UNIT_ASSERT(d.size() == 13); + UNIT_ASSERT(d[3] == 9); + UNIT_ASSERT(d[4] == 9); + + //Insertion of several elements at end: + d.insert(d.end(), 2, 10); + UNIT_ASSERT(d.size() == 15); + UNIT_ASSERT(d[14] == 10); + UNIT_ASSERT(d[13] == 10); + + //Insertion of several elements before last: + //There is more elements to insert than elements after insertion position + d.insert(d.end() - 1, 2, 11); + UNIT_ASSERT(d.size() == 17); + UNIT_ASSERT(d[15] == 11); + UNIT_ASSERT(d[14] == 11); + + //There is less elements to insert than elements after insertion position + d.insert(d.end() - 3, 2, 12); + UNIT_ASSERT(d.size() == 19); + UNIT_ASSERT(d[15] == 12); + UNIT_ASSERT(d[14] == 12); +} + +void TDequeTest::TestAt() { TDeque<int> d; TDeque<int> const& cd = d; - - d.push_back(10); - UNIT_ASSERT(d.at(0) == 10); - d.at(0) = 20; - UNIT_ASSERT(cd.at(0) == 20); - - for (;;) { - try { - d.at(1) = 20; - UNIT_ASSERT(false); - } catch (...) { - return; - } - } -} - -void TDequeTest::TestAutoRef() { - int i; + + d.push_back(10); + UNIT_ASSERT(d.at(0) == 10); + d.at(0) = 20; + UNIT_ASSERT(cd.at(0) == 20); + + for (;;) { + try { + d.at(1) = 20; + UNIT_ASSERT(false); + } catch (...) { + return; + } + } +} + +void TDequeTest::TestAutoRef() { + int i; TDeque<int> ref; - for (i = 0; i < 5; ++i) { - ref.push_back(i); - } - + for (i = 0; i < 5; ++i) { + ref.push_back(i); + } + TDeque<TDeque<int>> d_d_int(1, ref); - d_d_int.push_back(d_d_int[0]); - d_d_int.push_back(ref); - d_d_int.push_back(d_d_int[0]); - d_d_int.push_back(d_d_int[0]); - d_d_int.push_back(ref); - - for (i = 0; i < 5; ++i) { - UNIT_ASSERT(d_d_int[i] == ref); - } -} - -void TDequeTest::TestErase() { + d_d_int.push_back(d_d_int[0]); + d_d_int.push_back(ref); + d_d_int.push_back(d_d_int[0]); + d_d_int.push_back(d_d_int[0]); + d_d_int.push_back(ref); + + for (i = 0; i < 5; ++i) { + UNIT_ASSERT(d_d_int[i] == ref); + } +} + +void TDequeTest::TestErase() { TDeque<int> dint; - dint.push_back(3); - dint.push_front(2); - dint.push_back(4); - dint.push_front(1); - dint.push_back(5); - dint.push_front(0); - dint.push_back(6); - + dint.push_back(3); + dint.push_front(2); + dint.push_back(4); + dint.push_front(1); + dint.push_back(5); + dint.push_front(0); + dint.push_back(6); + TDeque<int>::iterator it(dint.begin() + 1); - UNIT_ASSERT(*it == 1); - - dint.erase(dint.begin()); - UNIT_ASSERT(*it == 1); - - it = dint.end() - 2; - UNIT_ASSERT(*it == 5); - - dint.erase(dint.end() - 1); - UNIT_ASSERT(*it == 5); - - dint.push_back(6); - dint.push_front(0); - - it = dint.begin() + 2; - UNIT_ASSERT(*it == 2); - - dint.erase(dint.begin(), dint.begin() + 2); - UNIT_ASSERT(*it == 2); - - it = dint.end() - 3; - UNIT_ASSERT(*it == 4); - - dint.erase(dint.end() - 2, dint.end()); - UNIT_ASSERT(*it == 4); -} + UNIT_ASSERT(*it == 1); + + dint.erase(dint.begin()); + UNIT_ASSERT(*it == 1); + + it = dint.end() - 2; + UNIT_ASSERT(*it == 5); + + dint.erase(dint.end() - 1); + UNIT_ASSERT(*it == 5); + + dint.push_back(6); + dint.push_front(0); + + it = dint.begin() + 2; + UNIT_ASSERT(*it == 2); + + dint.erase(dint.begin(), dint.begin() + 2); + UNIT_ASSERT(*it == 2); + + it = dint.end() - 3; + UNIT_ASSERT(*it == 4); + + dint.erase(dint.end() - 2, dint.end()); + UNIT_ASSERT(*it == 4); +} diff --git a/util/generic/explicit_type.h b/util/generic/explicit_type.h index 64dddd939a..34e269f155 100644 --- a/util/generic/explicit_type.h +++ b/util/generic/explicit_type.h @@ -20,10 +20,10 @@ * AnythingFunction(1ull); // Works. * @endcode */ -template <class T> +template <class T> class TExplicitType { public: - template <class OtherT> + template <class OtherT> TExplicitType(const OtherT& value, std::enable_if_t<std::is_same<OtherT, T>::value>* = nullptr) noexcept : Value_(value) { diff --git a/util/generic/explicit_type_ut.cpp b/util/generic/explicit_type_ut.cpp index 97ade0fde7..50a745f090 100644 --- a/util/generic/explicit_type_ut.cpp +++ b/util/generic/explicit_type_ut.cpp @@ -7,46 +7,46 @@ public: using TYes = char; using TNo = struct { TYes dummy[32]; }; - template <class T, class Arg> + template <class T, class Arg> static TNo Test(const T&, const Arg&, ...); - template <class T, class Arg> - static TYes Test(const T&, const Arg&, int, decltype(std::declval<T>()(std::declval<Arg>()))* = nullptr); + template <class T, class Arg> + static TYes Test(const T&, const Arg&, int, decltype(std::declval<T>()(std::declval<Arg>()))* = nullptr); }; -template <class T, class Arg> +template <class T, class Arg> struct TCallable: public TCallableBase { enum { Result = sizeof(Test(std::declval<T>(), std::declval<Arg>(), 1)) == sizeof(TYes) }; }; -template <class T> +template <class T> struct TExplicitlyCallable { - void operator()(TExplicitType<T>) { - } + void operator()(TExplicitType<T>) { + } }; struct IntConvertible { - operator int() { - return 1; - } + operator int() { + return 1; + } }; struct IntConstructible { - IntConstructible(const int&) { - } + IntConstructible(const int&) { + } }; Y_UNIT_TEST_SUITE(TestExplicitType) { Y_UNIT_TEST(Test1) { - UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<char>, char>::Result), true); - UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<char>, int>::Result), false); - UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<char>, wchar_t>::Result), false); - UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<int>, int>::Result), true); - UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<int>, IntConvertible>::Result), false); - UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<IntConstructible>, IntConstructible>::Result), true); - UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<IntConstructible>, IntConvertible>::Result), false); - UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<IntConstructible>, int>::Result), false); + UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<char>, char>::Result), true); + UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<char>, int>::Result), false); + UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<char>, wchar_t>::Result), false); + UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<int>, int>::Result), true); + UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<int>, IntConvertible>::Result), false); + UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<IntConstructible>, IntConstructible>::Result), true); + UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<IntConstructible>, IntConvertible>::Result), false); + UNIT_ASSERT_VALUES_EQUAL(static_cast<bool>(TCallable<TExplicitlyCallable<IntConstructible>, int>::Result), false); } } diff --git a/util/generic/fastqueue.cpp b/util/generic/fastqueue.cpp index e6a92fe21f..140b3ef63e 100644 --- a/util/generic/fastqueue.cpp +++ b/util/generic/fastqueue.cpp @@ -1 +1 @@ -#include "fastqueue.h" +#include "fastqueue.h" diff --git a/util/generic/fastqueue.h b/util/generic/fastqueue.h index 07e4993aa2..1fee5b86f6 100644 --- a/util/generic/fastqueue.h +++ b/util/generic/fastqueue.h @@ -1,7 +1,7 @@ #pragma once #include <util/memory/smallobj.h> -#include "ptr.h" +#include "ptr.h" template <class T> class TFastQueue { @@ -39,14 +39,14 @@ public: return Size_; } - Y_PURE_FUNCTION inline bool Empty() const noexcept { + Y_PURE_FUNCTION inline bool Empty() const noexcept { return !this->Size(); } inline explicit operator bool() const noexcept { - return !this->Empty(); - } - + return !this->Empty(); + } + private: typename THelper::TPool Pool_; TIntrusiveListWithAutoDelete<THelper, TDelete> Queue_; diff --git a/util/generic/flags.h b/util/generic/flags.h index da39a47e6f..a1f5921d42 100644 --- a/util/generic/flags.h +++ b/util/generic/flags.h @@ -127,12 +127,12 @@ public: } TFlags& operator&=(TFlags mask) { - *this = *this & mask; + *this = *this & mask; return *this; } TFlags& operator&=(Enum mask) { - *this = *this & mask; + *this = *this & mask; return *this; } @@ -184,12 +184,12 @@ public: private: struct TFlag { - constexpr TFlag() { - } - constexpr explicit TFlag(TInt value) - : Value(value) - { - } + constexpr TFlag() { + } + constexpr explicit TFlag(TInt value) + : Value(value) + { + } TInt Value = 0; }; diff --git a/util/generic/flags_ut.cpp b/util/generic/flags_ut.cpp index 200cce4b39..5377c6a058 100644 --- a/util/generic/flags_ut.cpp +++ b/util/generic/flags_ut.cpp @@ -2,7 +2,7 @@ #include "flags.h" -enum ETestFlag1: ui16 { +enum ETestFlag1: ui16 { Test1 = 1, Test2 = 2, Test4 = 4, @@ -24,9 +24,9 @@ Y_DECLARE_OPERATORS_FOR_FLAGS(ETest2) namespace { // won't compile without Y_DECLARE_UNUSED - enum class ETestFlag3 { One = 1, - Two = 2, - Three = 3 }; + enum class ETestFlag3 { One = 1, + Two = 2, + Three = 3 }; Y_DECLARE_FLAGS(ETestFlags3, ETestFlag3) Y_DECLARE_OPERATORS_FOR_FLAGS(ETestFlags3) } @@ -104,9 +104,9 @@ Y_UNIT_TEST_SUITE(TFlagsTest) { Y_UNIT_TEST(TestBaseType) { ui16 goodValue = 7; auto goodFlags = ETest1::FromBaseType(goodValue); - UNIT_ASSERT(goodFlags& ETestFlag1::Test1); - UNIT_ASSERT(goodFlags& ETestFlag1::Test2); - UNIT_ASSERT(goodFlags& ETestFlag1::Test4); + UNIT_ASSERT(goodFlags& ETestFlag1::Test1); + UNIT_ASSERT(goodFlags& ETestFlag1::Test2); + UNIT_ASSERT(goodFlags& ETestFlag1::Test4); UNIT_ASSERT_VALUES_EQUAL(goodValue, goodFlags.ToBaseType()); // Passed value is not checked, but preserved as is diff --git a/util/generic/function.cpp b/util/generic/function.cpp index a29ca4ef5c..d4b693e3fa 100644 --- a/util/generic/function.cpp +++ b/util/generic/function.cpp @@ -1 +1 @@ -#include "function.h" +#include "function.h" diff --git a/util/generic/function.h b/util/generic/function.h index 3a90758741..62fa84e0cb 100644 --- a/util/generic/function.h +++ b/util/generic/function.h @@ -1,26 +1,26 @@ -#pragma once - -#include "typetraits.h" -#include "typelist.h" - -#include <functional> - -namespace NPrivate { - template <class F> - struct TRemoveClassImpl { - using TSignature = F; - }; - - template <typename C, typename R, typename... Args> - struct TRemoveClassImpl<R (C::*)(Args...)> { - typedef R TSignature(Args...); - }; - - template <typename C, typename R, typename... Args> - struct TRemoveClassImpl<R (C::*)(Args...) const> { - typedef R TSignature(Args...); - }; - +#pragma once + +#include "typetraits.h" +#include "typelist.h" + +#include <functional> + +namespace NPrivate { + template <class F> + struct TRemoveClassImpl { + using TSignature = F; + }; + + template <typename C, typename R, typename... Args> + struct TRemoveClassImpl<R (C::*)(Args...)> { + typedef R TSignature(Args...); + }; + + template <typename C, typename R, typename... Args> + struct TRemoveClassImpl<R (C::*)(Args...) const> { + typedef R TSignature(Args...); + }; + template <class T> struct TRemoveNoExceptImpl { using Type = T; @@ -39,49 +39,49 @@ namespace NPrivate { template <class T> using TRemoveNoExcept = typename TRemoveNoExceptImpl<T>::Type; - template <class F> + template <class F> using TRemoveClass = typename TRemoveClassImpl<TRemoveNoExcept<F>>::TSignature; - - template <class C> - struct TFuncInfo { - using TSignature = TRemoveClass<decltype(&C::operator())>; - }; - - template <class R, typename... Args> - struct TFuncInfo<R(Args...)> { - using TResult = R; - typedef R TSignature(Args...); - }; -} - -template <class C> -using TFunctionSignature = typename ::NPrivate::TFuncInfo<::NPrivate::TRemoveClass<std::remove_reference_t<std::remove_pointer_t<C>>>>::TSignature; - -template <typename F> -struct TCallableTraits: public TCallableTraits<TFunctionSignature<F>> { -}; - -template <typename R, typename... Args> -struct TCallableTraits<R(Args...)> { - using TResult = R; - using TArgs = TTypeList<Args...>; - typedef R TSignature(Args...); -}; - -template <typename C> -using TFunctionResult = typename TCallableTraits<C>::TResult; - -template <typename C> -using TFunctionArgs = typename TCallableTraits<C>::TArgs; - -template <typename C, size_t N> -struct TFunctionArgImpl { - using TArgs = TFunctionArgs<C>; - using TResult = typename TArgs::template TGet<N>; -}; - -template <typename C, size_t N> -using TFunctionArg = typename TFunctionArgImpl<C, N>::TResult; + + template <class C> + struct TFuncInfo { + using TSignature = TRemoveClass<decltype(&C::operator())>; + }; + + template <class R, typename... Args> + struct TFuncInfo<R(Args...)> { + using TResult = R; + typedef R TSignature(Args...); + }; +} + +template <class C> +using TFunctionSignature = typename ::NPrivate::TFuncInfo<::NPrivate::TRemoveClass<std::remove_reference_t<std::remove_pointer_t<C>>>>::TSignature; + +template <typename F> +struct TCallableTraits: public TCallableTraits<TFunctionSignature<F>> { +}; + +template <typename R, typename... Args> +struct TCallableTraits<R(Args...)> { + using TResult = R; + using TArgs = TTypeList<Args...>; + typedef R TSignature(Args...); +}; + +template <typename C> +using TFunctionResult = typename TCallableTraits<C>::TResult; + +template <typename C> +using TFunctionArgs = typename TCallableTraits<C>::TArgs; + +template <typename C, size_t N> +struct TFunctionArgImpl { + using TArgs = TFunctionArgs<C>; + using TResult = typename TArgs::template TGet<N>; +}; + +template <typename C, size_t N> +using TFunctionArg = typename TFunctionArgImpl<C, N>::TResult; // temporary before std::apply appearance @@ -92,12 +92,12 @@ auto ApplyImpl(F&& f, Tuple&& t, std::index_sequence<I...>) { // change to std::apply after c++ 17 template <typename F, typename Tuple> -auto Apply(F&& f, Tuple&& t) { - return ApplyImpl(f, t, std::make_index_sequence<std::tuple_size<std::decay_t<Tuple>>::value>{}); +auto Apply(F&& f, Tuple&& t) { + return ApplyImpl(f, t, std::make_index_sequence<std::tuple_size<std::decay_t<Tuple>>::value>{}); } // change to std::apply after c++ 17 template <typename F> -auto Apply(F&& f, std::tuple<>) { +auto Apply(F&& f, std::tuple<>) { return f(); } diff --git a/util/generic/function_ut.cpp b/util/generic/function_ut.cpp index 8c70109737..3880295a9f 100644 --- a/util/generic/function_ut.cpp +++ b/util/generic/function_ut.cpp @@ -1,69 +1,69 @@ -#include "function.h" -#include "typetraits.h" - +#include "function.h" +#include "typetraits.h" + #include <library/cpp/testing/unittest/registar.h> - + Y_UNIT_TEST_SUITE(TestFunctionSignature) { - int FF(double x) { - return (int)x; - } - - int FFF(double x, char xx) { - return (int)x + (int)xx; - } - - struct A { - int F(double x) { - return FF(x); - } - }; - + int FF(double x) { + return (int)x; + } + + int FFF(double x, char xx) { + return (int)x + (int)xx; + } + + struct A { + int F(double x) { + return FF(x); + } + }; + Y_UNIT_TEST(TestPlainFunc) { - UNIT_ASSERT_TYPES_EQUAL(TFunctionSignature<decltype(FF)>, decltype(FF)); - } - + UNIT_ASSERT_TYPES_EQUAL(TFunctionSignature<decltype(FF)>, decltype(FF)); + } + Y_UNIT_TEST(TestMethod) { - UNIT_ASSERT_TYPES_EQUAL(TFunctionSignature<decltype(&A::F)>, decltype(FF)); - } - + UNIT_ASSERT_TYPES_EQUAL(TFunctionSignature<decltype(&A::F)>, decltype(FF)); + } + Y_UNIT_TEST(TestLambda) { - auto f = [](double x) -> int { - return FF(x); - }; - - UNIT_ASSERT_TYPES_EQUAL(TFunctionSignature<decltype(f)>, decltype(FF)); - } - + auto f = [](double x) -> int { + return FF(x); + }; + + UNIT_ASSERT_TYPES_EQUAL(TFunctionSignature<decltype(f)>, decltype(FF)); + } + Y_UNIT_TEST(TestFunction) { std::function<int(double)> f(FF); - - UNIT_ASSERT_TYPES_EQUAL(TFunctionSignature<decltype(f)>, decltype(FF)); - } - - template <class F> - void TestCT() { -#define FA(x) TFunctionArg<F, x> - - UNIT_ASSERT_TYPES_EQUAL(FA(0), double); - UNIT_ASSERT_TYPES_EQUAL(FA(1), char); - UNIT_ASSERT_TYPES_EQUAL(TFunctionResult<F>, int); - -#undef FA - } - + + UNIT_ASSERT_TYPES_EQUAL(TFunctionSignature<decltype(f)>, decltype(FF)); + } + + template <class F> + void TestCT() { +#define FA(x) TFunctionArg<F, x> + + UNIT_ASSERT_TYPES_EQUAL(FA(0), double); + UNIT_ASSERT_TYPES_EQUAL(FA(1), char); + UNIT_ASSERT_TYPES_EQUAL(TFunctionResult<F>, int); + +#undef FA + } + Y_UNIT_TEST(TestTypeErasureTraits) { - TestCT<std::function<int(double, char)>>(); - } - + TestCT<std::function<int(double, char)>>(); + } + Y_UNIT_TEST(TestPlainFunctionTraits) { - TestCT<decltype(FFF)>(); - } - + TestCT<decltype(FFF)>(); + } + Y_UNIT_TEST(TestLambdaTraits) { - auto fff = [](double xx, char xxx) -> int { - return FFF(xx, xxx); - }; - - TestCT<decltype(fff)>(); - } -} + auto fff = [](double xx, char xxx) -> int { + return FFF(xx, xxx); + }; + + TestCT<decltype(fff)>(); + } +} diff --git a/util/generic/fuzz/vector/main.cpp b/util/generic/fuzz/vector/main.cpp index 9d3211da96..0a0293f795 100644 --- a/util/generic/fuzz/vector/main.cpp +++ b/util/generic/fuzz/vector/main.cpp @@ -1,47 +1,47 @@ -#include <util/generic/vector.h> -#include <util/stream/mem.h> - -template <class T> +#include <util/generic/vector.h> +#include <util/stream/mem.h> + +template <class T> static inline T Read(IInputStream& in) { - T t; - - in.LoadOrFail(&t, sizeof(t)); - - return t; -} - -extern "C" int LLVMFuzzerTestOneInput(const ui8* data, size_t size) { - TMemoryInput mi(data, size); - - try { + T t; + + in.LoadOrFail(&t, sizeof(t)); + + return t; +} + +extern "C" int LLVMFuzzerTestOneInput(const ui8* data, size_t size) { + TMemoryInput mi(data, size); + + try { TVector<ui16> v; - - while (mi.Avail()) { - char cmd = Read<char>(mi); - - switch (cmd % 2) { - case 0: { - const size_t cnt = 1 + Read<ui8>(mi) % 16; - - for (size_t i = 0; i < cnt; ++i) { - v.push_back(i); - } - - break; - } - - case 1: { - if (v) { - v.pop_back(); - } - - break; - } - } - } - } catch (...) { - // ¯\_(ツ)_/¯ - } - - return 0; // Non-zero return values are reserved for future use. -} + + while (mi.Avail()) { + char cmd = Read<char>(mi); + + switch (cmd % 2) { + case 0: { + const size_t cnt = 1 + Read<ui8>(mi) % 16; + + for (size_t i = 0; i < cnt; ++i) { + v.push_back(i); + } + + break; + } + + case 1: { + if (v) { + v.pop_back(); + } + + break; + } + } + } + } catch (...) { + // ¯\_(ツ)_/¯ + } + + return 0; // Non-zero return values are reserved for future use. +} diff --git a/util/generic/fuzz/vector/ya.make b/util/generic/fuzz/vector/ya.make index 14986170eb..b8614f6411 100644 --- a/util/generic/fuzz/vector/ya.make +++ b/util/generic/fuzz/vector/ya.make @@ -1,13 +1,13 @@ FUZZ() - + OWNER( pg g:util ) SUBSCRIBER(g:util-subscribers) - -SRCS( - main.cpp -) - -END() + +SRCS( + main.cpp +) + +END() diff --git a/util/generic/fuzz/ya.make b/util/generic/fuzz/ya.make index 947437e0eb..dc60b12a0c 100644 --- a/util/generic/fuzz/ya.make +++ b/util/generic/fuzz/ya.make @@ -1,3 +1,3 @@ -RECURSE( - vector -) +RECURSE( + vector +) diff --git a/util/generic/fwd.cpp b/util/generic/fwd.cpp index 2261ef316c..4214b6df83 100644 --- a/util/generic/fwd.cpp +++ b/util/generic/fwd.cpp @@ -1 +1 @@ -#include "fwd.h" +#include "fwd.h" diff --git a/util/generic/fwd.h b/util/generic/fwd.h index 6111c47fa3..5cc2da40e5 100644 --- a/util/generic/fwd.h +++ b/util/generic/fwd.h @@ -1,7 +1,7 @@ -#pragma once - -#include <util/system/defaults.h> - +#pragma once + +#include <util/system/defaults.h> + #include <stlfwd> template <typename TCharType, typename TTraits = std::char_traits<TCharType>> @@ -18,9 +18,9 @@ using TStringBuf = TBasicStringBuf<char>; using TWtringBuf = TBasicStringBuf<wchar16>; using TUtf32StringBuf = TBasicStringBuf<wchar32>; -//misc -class TBuffer; - +//misc +class TBuffer; + //functors template <class T = void> struct TLess; @@ -34,23 +34,23 @@ struct TEqualTo; template <class T> struct THash; -//intrusive containers +//intrusive containers struct TIntrusiveListDefaultTag; template <class T, class Tag = TIntrusiveListDefaultTag> -class TIntrusiveList; - +class TIntrusiveList; + template <class T, class D, class Tag = TIntrusiveListDefaultTag> -class TIntrusiveListWithAutoDelete; - +class TIntrusiveListWithAutoDelete; + template <class T, class Tag = TIntrusiveListDefaultTag> -class TIntrusiveSList; - -template <class T, class C> -class TAvlTree; - -template <class TValue, class TCmp> -class TRbTree; - +class TIntrusiveSList; + +template <class T, class C> +class TAvlTree; + +template <class TValue, class TCmp> +class TRbTree; + //containers template <class T, class A = std::allocator<T>> class TVector; @@ -72,7 +72,7 @@ class THashMultiMap; template <class Value, class HashFcn = THash<Value>, class EqualKey = TEqualTo<Value>, class Alloc = std::allocator<Value>> class THashSet; - + template <class Value, class HashFcn = THash<Value>, class EqualKey = TEqualTo<Value>, class Alloc = std::allocator<Value>> class THashMultiSet; @@ -95,32 +95,32 @@ template <class T, class S = TDeque<T>> class TStack; template <size_t BitCount, typename TChunkType = ui64> -class TBitMap; - -//autopointers +class TBitMap; + +//autopointers class TDelete; class TDeleteArray; class TFree; class TCopyNew; template <class T, class D = TDelete> -class TAutoPtr; - +class TAutoPtr; + template <class T, class D = TDelete> -class THolder; - +class THolder; + template <class T, class C, class D = TDelete> -class TRefCounted; - +class TRefCounted; + template <class T> class TDefaultIntrusivePtrOps; -template <class T, class Ops> +template <class T, class Ops> class TSimpleIntrusiveOps; template <class T, class Ops = TDefaultIntrusivePtrOps<T>> -class TIntrusivePtr; - +class TIntrusivePtr; + template <class T, class Ops = TDefaultIntrusivePtrOps<T>> class TIntrusiveConstPtr; @@ -128,10 +128,10 @@ template <class T, class Ops = TDefaultIntrusivePtrOps<T>> using TSimpleIntrusivePtr = TIntrusivePtr<T, TSimpleIntrusiveOps<T, Ops>>; template <class T, class C, class D = TDelete> -class TSharedPtr; - +class TSharedPtr; + template <class T, class C = TCopyNew, class D = TDelete> -class TCopyPtr; +class TCopyPtr; template <class TPtr, class TCopy = TCopyNew> class TCowPtr; diff --git a/util/generic/guid.cpp b/util/generic/guid.cpp index 98eddbd533..8b907457bc 100644 --- a/util/generic/guid.cpp +++ b/util/generic/guid.cpp @@ -1,12 +1,12 @@ #include "guid.h" -#include "ylimits.h" +#include "ylimits.h" #include "string.h" - -#include <util/string/ascii.h> + +#include <util/string/ascii.h> #include <util/string/builder.h> -#include <util/stream/format.h> -#include <util/system/unaligned_mem.h> -#include <util/random/easy.h> +#include <util/stream/format.h> +#include <util/system/unaligned_mem.h> +#include <util/random/easy.h> namespace { inline void LowerCaseHex(TString& s) { @@ -41,9 +41,9 @@ TGUID TGUID::Create() { return result; } -void CreateGuid(TGUID* res) { +void CreateGuid(TGUID* res) { ui64* dw = reinterpret_cast<ui64*>(res->dw); - + WriteUnaligned<ui64>(&dw[0], RandomNumber<ui64>()); WriteUnaligned<ui64>(&dw[1], RandomNumber<ui64>()); } @@ -91,13 +91,13 @@ bool GetGuid(const TStringBuf s, TGUID& result) { size_t partId = 0; ui64 partValue = 0; bool isEmptyPart = true; - + for (size_t i = 0; i != s.size(); ++i) { const char c = s[i]; if (c == '-') { - if (isEmptyPart || partId == 3) { // x-y--z, -x-y-z or x-y-z-m-... - return false; + if (isEmptyPart || partId == 3) { // x-y--z, -x-y-z or x-y-z-m-... + return false; } result.dw[partId] = static_cast<ui32>(partValue); ++partId; @@ -115,29 +115,29 @@ bool GetGuid(const TStringBuf s, TGUID& result) { isEmptyPart = false; // overflow check - if (partValue > Max<ui32>()) { - return false; + if (partValue > Max<ui32>()) { + return false; } } - if (partId != 3 || isEmptyPart) { // x-y or x-y-z- - return false; + if (partId != 3 || isEmptyPart) { // x-y or x-y-z- + return false; } result.dw[partId] = static_cast<ui32>(partValue); - return true; + return true; } - -// Parses GUID from s and checks that it's valid. -// In case of error returns TGUID(). + +// Parses GUID from s and checks that it's valid. +// In case of error returns TGUID(). TGUID GetGuid(const TStringBuf s) { - TGUID result; - - if (GetGuid(s, result)) { - return result; - } - - return TGUID(); -} + TGUID result; + + if (GetGuid(s, result)) { + return result; + } + + return TGUID(); +} bool GetUuid(const TStringBuf s, TGUID& result) { if (s.size() != 36) { diff --git a/util/generic/guid.h b/util/generic/guid.h index 9f1adf1f61..2bf6c8ad99 100644 --- a/util/generic/guid.h +++ b/util/generic/guid.h @@ -3,7 +3,7 @@ #include "fwd.h" #include <util/str_stl.h> - + /** * UUID generation * @@ -14,16 +14,16 @@ * See https://clubs.at.yandex-team.ru/stackoverflow/10238/10240 * and https://st.yandex-team.ru/IGNIETFERRO-768 for details. */ -struct TGUID { +struct TGUID { ui32 dw[4] = {}; constexpr bool IsEmpty() const noexcept { - return (dw[0] | dw[1] | dw[2] | dw[3]) == 0; - } - + return (dw[0] | dw[1] | dw[2] | dw[3]) == 0; + } + constexpr explicit operator bool() const noexcept { - return !IsEmpty(); - } + return !IsEmpty(); + } // xxxx-xxxx-xxxx-xxxx TString AsGuidString() const; @@ -43,29 +43,29 @@ struct TGUID { **/ static TGUID CreateTimebased(); }; - + constexpr bool operator==(const TGUID& a, const TGUID& b) noexcept { return a.dw[0] == b.dw[0] && a.dw[1] == b.dw[1] && a.dw[2] == b.dw[2] && a.dw[3] == b.dw[3]; -} - +} + constexpr bool operator!=(const TGUID& a, const TGUID& b) noexcept { - return !(a == b); -} - -struct TGUIDHash { + return !(a == b); +} + +struct TGUIDHash { constexpr int operator()(const TGUID& a) const noexcept { - return a.dw[0] + a.dw[1] + a.dw[2] + a.dw[3]; - } + return a.dw[0] + a.dw[1] + a.dw[2] + a.dw[3]; + } }; - + template <> -struct THash<TGUID> { +struct THash<TGUID> { constexpr size_t operator()(const TGUID& g) const noexcept { return (unsigned int)TGUIDHash()(g); } }; -void CreateGuid(TGUID* res); +void CreateGuid(TGUID* res); TString GetGuidAsString(const TGUID& g); TString CreateGuidAsString(); TGUID GetGuid(TStringBuf s); diff --git a/util/generic/guid_ut.cpp b/util/generic/guid_ut.cpp index e9911e1012..048354ff39 100644 --- a/util/generic/guid_ut.cpp +++ b/util/generic/guid_ut.cpp @@ -1,94 +1,94 @@ #include <library/cpp/testing/unittest/registar.h> - -#include "guid.h" - + +#include "guid.h" + Y_UNIT_TEST_SUITE(TGuidTest) { - //TODO - make real constructor - static TGUID Construct(ui32 d1, ui32 d2, ui32 d3, ui32 d4) { - TGUID ret; - - ret.dw[0] = d1; - ret.dw[1] = d2; - ret.dw[2] = d3; - ret.dw[3] = d4; - - return ret; - } - - struct TTest { - TGUID G; + //TODO - make real constructor + static TGUID Construct(ui32 d1, ui32 d2, ui32 d3, ui32 d4) { + TGUID ret; + + ret.dw[0] = d1; + ret.dw[1] = d2; + ret.dw[2] = d3; + ret.dw[3] = d4; + + return ret; + } + + struct TTest { + TGUID G; TString S; - }; - + }; + Y_UNIT_TEST(Test1) { - for (size_t i = 0; i < 1000; ++i) { - TGUID g; - - CreateGuid(&g); - - UNIT_ASSERT_EQUAL(g, GetGuid(GetGuidAsString(g))); - } - } - + for (size_t i = 0; i < 1000; ++i) { + TGUID g; + + CreateGuid(&g); + + UNIT_ASSERT_EQUAL(g, GetGuid(GetGuidAsString(g))); + } + } + Y_UNIT_TEST(Test2) { - const TTest tests[] = { - {Construct(1, 1, 1, 1), "1-1-1-1"}, - {Construct(0, 0, 0, 0), "0-0-0-0"}, - {TGUID(), "H-0-0-0"}, - {TGUID(), "0-H-0-0"}, - {TGUID(), "0-0-H-0"}, - {TGUID(), "0-0-0-H"}, - {Construct(0x8cf813d9U, 0xc098da90U, 0x7ef58954U, 0x636d04dU), "8cf813d9-c098da90-7ef58954-636d04d"}, - {Construct(0x8cf813d9U, 0xc098da90U, 0x7ef58954U, 0x636d04dU), "8CF813D9-C098DA90-7EF58954-636D04D"}, - {Construct(0x12345678U, 0x90abcdefU, 0xfedcba09U, 0x87654321U), "12345678-90abcdef-FEDCBA09-87654321"}, - {Construct(0x1, 0x2, 0xabcdef, 0x400), "01-002-00ABCDEF-000400"}, - {TGUID(), "-1-1-1"}, // empty parts - {TGUID(), "--1-1-1"}, - {TGUID(), "1--1-1"}, - {TGUID(), "1-1"}, // unexpected end - {TGUID(), "1-1-"}, + const TTest tests[] = { + {Construct(1, 1, 1, 1), "1-1-1-1"}, + {Construct(0, 0, 0, 0), "0-0-0-0"}, + {TGUID(), "H-0-0-0"}, + {TGUID(), "0-H-0-0"}, + {TGUID(), "0-0-H-0"}, + {TGUID(), "0-0-0-H"}, + {Construct(0x8cf813d9U, 0xc098da90U, 0x7ef58954U, 0x636d04dU), "8cf813d9-c098da90-7ef58954-636d04d"}, + {Construct(0x8cf813d9U, 0xc098da90U, 0x7ef58954U, 0x636d04dU), "8CF813D9-C098DA90-7EF58954-636D04D"}, + {Construct(0x12345678U, 0x90abcdefU, 0xfedcba09U, 0x87654321U), "12345678-90abcdef-FEDCBA09-87654321"}, + {Construct(0x1, 0x2, 0xabcdef, 0x400), "01-002-00ABCDEF-000400"}, + {TGUID(), "-1-1-1"}, // empty parts + {TGUID(), "--1-1-1"}, + {TGUID(), "1--1-1"}, + {TGUID(), "1-1"}, // unexpected end + {TGUID(), "1-1-"}, {TGUID(), "1-1-1"}, - {TGUID(), "1-1-1-"}, - {TGUID(), "1-1-1-1-"}, - {TGUID(), "1-1-1-1-1"}, - {TGUID(), "1+1-1-1"}, // bad char - {TGUID(), "1-1:3-1-1"}, - {Construct(0xffffffffU, 0xffffffffU, 0xffffffffU, 0xffffffffU), "FFFFFFFF-FFFFFFFF-FFFFFFFF-FFFFFFFF"}, // overflow - {TGUID(), "FFFFFFFFA-FFFFFFFF-FFFFFFFF-FFFFFFFF"}, - {TGUID(), "100000000-0-0-0"}, - {Construct(1, 1, 1, 1), "0000001-0000000000000000000000000000000000000001-0001-00000001"}, - {Construct(0, 0, 0, 0), "000000000000-000000000000000000000000000000000000000-000-0"}, - }; - + {TGUID(), "1-1-1-"}, + {TGUID(), "1-1-1-1-"}, + {TGUID(), "1-1-1-1-1"}, + {TGUID(), "1+1-1-1"}, // bad char + {TGUID(), "1-1:3-1-1"}, + {Construct(0xffffffffU, 0xffffffffU, 0xffffffffU, 0xffffffffU), "FFFFFFFF-FFFFFFFF-FFFFFFFF-FFFFFFFF"}, // overflow + {TGUID(), "FFFFFFFFA-FFFFFFFF-FFFFFFFF-FFFFFFFF"}, + {TGUID(), "100000000-0-0-0"}, + {Construct(1, 1, 1, 1), "0000001-0000000000000000000000000000000000000001-0001-00000001"}, + {Construct(0, 0, 0, 0), "000000000000-000000000000000000000000000000000000000-000-0"}, + }; + for (const auto& t : tests) { - UNIT_ASSERT_EQUAL(t.G, GetGuid(t.S)); - } - } - + UNIT_ASSERT_EQUAL(t.G, GetGuid(t.S)); + } + } + Y_UNIT_TEST(Test3) { - //if this test failed, please, fix buffer size in GetGuidAsString() - TGUID max = Construct(Max<ui32>(), Max<ui32>(), Max<ui32>(), Max<ui32>()); - - UNIT_ASSERT_EQUAL(GetGuidAsString(max).length(), 35); - } - + //if this test failed, please, fix buffer size in GetGuidAsString() + TGUID max = Construct(Max<ui32>(), Max<ui32>(), Max<ui32>(), Max<ui32>()); + + UNIT_ASSERT_EQUAL(GetGuidAsString(max).length(), 35); + } + Y_UNIT_TEST(Test4) { - UNIT_ASSERT_VALUES_EQUAL(GetGuidAsString(Construct(1, 2, 3, 4)), "1-2-3-4"); - UNIT_ASSERT_VALUES_EQUAL(GetGuidAsString(Construct(1, 2, 0xFFFFFF, 4)), "1-2-ffffff-4"); - UNIT_ASSERT_VALUES_EQUAL(GetGuidAsString(Construct(0xFAFA, 2, 3, 4)), "fafa-2-3-4"); - UNIT_ASSERT_VALUES_EQUAL(GetGuidAsString(Construct(1, 0xADE, 3, 4)), "1-ade-3-4"); - UNIT_ASSERT_VALUES_EQUAL(GetGuidAsString(Construct(1, 2, 3, 0xDEAD)), "1-2-3-dead"); - } + UNIT_ASSERT_VALUES_EQUAL(GetGuidAsString(Construct(1, 2, 3, 4)), "1-2-3-4"); + UNIT_ASSERT_VALUES_EQUAL(GetGuidAsString(Construct(1, 2, 0xFFFFFF, 4)), "1-2-ffffff-4"); + UNIT_ASSERT_VALUES_EQUAL(GetGuidAsString(Construct(0xFAFA, 2, 3, 4)), "fafa-2-3-4"); + UNIT_ASSERT_VALUES_EQUAL(GetGuidAsString(Construct(1, 0xADE, 3, 4)), "1-ade-3-4"); + UNIT_ASSERT_VALUES_EQUAL(GetGuidAsString(Construct(1, 2, 3, 0xDEAD)), "1-2-3-dead"); + } Y_UNIT_TEST(Test5) { const TTest tests[] = { {TGUID(), "1-1-1-1-1"}, - {TGUID(), "00000001-0001-0001-0001-00000000001-"}, + {TGUID(), "00000001-0001-0001-0001-00000000001-"}, {Construct(0x10000001U, 0x10011001U, 0x10011001U, 0x10000001U), "10000001-1001-1001-1001-100110000001"}, {Construct(0x550e8400U, 0xe29b41d4U, 0xa7164466U, 0x55440000U), "550e8400-e29b-41d4-a716-446655440000"}, {Construct(0xffffffffU, 0xffffffffU, 0xffffffffU, 0xffffffffU), "ffffffff-ffff-ffff-ffff-ffffffffffff"}, {TGUID(), "ffffffff-ffffff-ff-ffff-ffffffffffff"}, - {TGUID(), "ffffffff-ffff-ffff-ff-ffffffffffffff"}}; + {TGUID(), "ffffffff-ffff-ffff-ff-ffffffffffffff"}}; for (const auto& t : tests) { UNIT_ASSERT_EQUAL(t.G, GetUuid(t.S)); @@ -125,4 +125,4 @@ Y_UNIT_TEST_SUITE(TGuidTest) { UNIT_ASSERT(!guid.empty()); UNIT_ASSERT_EQUAL(guid[14], '1'); } -} +} diff --git a/util/generic/hash.h b/util/generic/hash.h index 532cf16b68..e46db21fa9 100644 --- a/util/generic/hash.h +++ b/util/generic/hash.h @@ -1,45 +1,45 @@ -#pragma once - +#pragma once + #include "fwd.h" #include "mapfindptr.h" #include <util/memory/alloc.h> #include <util/system/type_name.h> -#include <util/system/yassert.h> -#include <util/str_stl.h> -#include "yexception.h" -#include "typetraits.h" -#include "utility.h" - -#include <algorithm> +#include <util/system/yassert.h> +#include <util/str_stl.h> +#include "yexception.h" +#include "typetraits.h" +#include "utility.h" + +#include <algorithm> #include <initializer_list> #include <memory> #include <tuple> #include <utility> - -#include <cstdlib> - + +#include <cstdlib> + #include "hash_primes.h" -struct TSelect1st { - template <class TPair> - inline const typename TPair::first_type& operator()(const TPair& x) const { - return x.first; - } -}; - +struct TSelect1st { + template <class TPair> + inline const typename TPair::first_type& operator()(const TPair& x) const { + return x.first; + } +}; + template <class Value> struct __yhashtable_node { - /** If the first bit is not set, then this is a pointer to the next node in - * the list of nodes for the current bucket. Otherwise this is a pointer of + /** If the first bit is not set, then this is a pointer to the next node in + * the list of nodes for the current bucket. Otherwise this is a pointer of * type __yhashtable_node**, pointing back into the buckets array. - * - * This trick makes it possible to use only one node pointer in a hash table - * iterator. */ + * + * This trick makes it possible to use only one node pointer in a hash table + * iterator. */ __yhashtable_node* next; - /** Value stored in a node. */ - Value val; + /** Value stored in a node. */ + Value val; __yhashtable_node& operator=(const __yhashtable_node&) = delete; }; @@ -64,41 +64,41 @@ struct __yhashtable_iterator { using const_iterator = __yhashtable_const_iterator<Value>; using node = __yhashtable_node<Value>; - using iterator_category = std::forward_iterator_tag; + using iterator_category = std::forward_iterator_tag; using value_type = Value; using difference_type = ptrdiff_t; using size_type = size_t; using reference = Value&; using pointer = Value*; - node* cur; + node* cur; explicit __yhashtable_iterator(node* n) - : cur(n) - { - } /*y*/ + : cur(n) + { + } /*y*/ __yhashtable_iterator() = default; - reference operator*() const { - return cur->val; - } - pointer operator->() const { - return &(operator*()); - } - iterator& operator++(); - iterator operator++(int); - bool operator==(const iterator& it) const { - return cur == it.cur; - } - bool operator!=(const iterator& it) const { - return cur != it.cur; - } - bool IsEnd() const { - return !cur; - } + reference operator*() const { + return cur->val; + } + pointer operator->() const { + return &(operator*()); + } + iterator& operator++(); + iterator operator++(int); + bool operator==(const iterator& it) const { + return cur == it.cur; + } + bool operator!=(const iterator& it) const { + return cur != it.cur; + } + bool IsEnd() const { + return !cur; + } Y_FORCE_INLINE explicit operator bool() const noexcept { return cur != nullptr; - } + } }; template <class Value> @@ -107,45 +107,45 @@ struct __yhashtable_const_iterator { using const_iterator = __yhashtable_const_iterator<Value>; using node = __yhashtable_node<Value>; - using iterator_category = std::forward_iterator_tag; + using iterator_category = std::forward_iterator_tag; using value_type = Value; using difference_type = ptrdiff_t; using size_type = size_t; using reference = const Value&; using pointer = const Value*; - const node* cur; + const node* cur; explicit __yhashtable_const_iterator(const node* n) - : cur(n) - { - } + : cur(n) + { + } __yhashtable_const_iterator() { - } + } __yhashtable_const_iterator(const iterator& it) - : cur(it.cur) - { - } - reference operator*() const { - return cur->val; - } - pointer operator->() const { - return &(operator*()); - } - const_iterator& operator++(); - const_iterator operator++(int); - bool operator==(const const_iterator& it) const { - return cur == it.cur; - } - bool operator!=(const const_iterator& it) const { - return cur != it.cur; - } - bool IsEnd() const { - return !cur; - } + : cur(it.cur) + { + } + reference operator*() const { + return cur->val; + } + pointer operator->() const { + return &(operator*()); + } + const_iterator& operator++(); + const_iterator operator++(int); + bool operator==(const const_iterator& it) const { + return cur == it.cur; + } + bool operator!=(const const_iterator& it) const { + return cur != it.cur; + } + bool IsEnd() const { + return !cur; + } Y_FORCE_INLINE explicit operator bool() const noexcept { return cur != nullptr; - } + } }; /** @@ -153,27 +153,27 @@ struct __yhashtable_const_iterator { * use case of empty allocators. This is achieved thanks to the application of * empty base class optimization (aka EBCO). */ -template <class Alloc> +template <class Alloc> class _allocator_base: private Alloc { public: _allocator_base(const Alloc& other) : Alloc(other) - { - } - - Alloc& _get_alloc() { - return static_cast<Alloc&>(*this); - } - const Alloc& _get_alloc() const { - return static_cast<const Alloc&>(*this); - } - void _set_alloc(const Alloc& allocator) { - _get_alloc() = allocator; - } - - void swap(_allocator_base& other) { - DoSwap(_get_alloc(), other._get_alloc()); - } + { + } + + Alloc& _get_alloc() { + return static_cast<Alloc&>(*this); + } + const Alloc& _get_alloc() const { + return static_cast<const Alloc&>(*this); + } + void _set_alloc(const Alloc& allocator) { + _get_alloc() = allocator; + } + + void swap(_allocator_base& other) { + DoSwap(_get_alloc(), other._get_alloc()); + } }; /** @@ -202,11 +202,11 @@ public: * * Unused space at the end of the memory block may not be present. */ -template <class T, class Alloc> +template <class T, class Alloc> class _yhashtable_buckets: private _allocator_base<Alloc> { using base_type = _allocator_base<Alloc>; - static_assert(sizeof(T) == sizeof(size_t), "T is expected to be the same size as size_t."); + static_assert(sizeof(T) == sizeof(size_t), "T is expected to be the same size as size_t."); public: using allocator_type = Alloc; @@ -225,76 +225,76 @@ public: : base_type(other) , Data(nullptr) , Size() - { - } + { + } ~_yhashtable_buckets() { Y_ASSERT(!Data); - } + } void initialize_dynamic(TBucketDivisor size) { Y_ASSERT(!Data); Data = this->_get_alloc().allocate(size() + 2) + 1; - Size = size; + Size = size; *reinterpret_cast<size_type*>(Data - 1) = size() + 2; - } + } - void deinitialize_dynamic() { + void deinitialize_dynamic() { Y_ASSERT(Data); - this->_get_alloc().deallocate(Data - 1, *reinterpret_cast<size_type*>(Data - 1)); - Data = pointer(); + this->_get_alloc().deallocate(Data - 1, *reinterpret_cast<size_type*>(Data - 1)); + Data = pointer(); Size = TBucketDivisor(); - } + } void initialize_static(pointer data, TBucketDivisor size) { Y_ASSERT(!Data && data && size() >= 1); - Data = data; - Size = size; - } + Data = data; + Size = size; + } - void deinitialize_static() { + void deinitialize_static() { Y_ASSERT(Data); - Data = pointer(); + Data = pointer(); Size = TBucketDivisor(); - } + } void resize_noallocate(TBucketDivisor size) { Y_ASSERT(size() <= capacity()); - Size = size; - } + Size = size; + } - iterator begin() { - return Data; - } - const_iterator begin() const { - return Data; - } - iterator end() { + iterator begin() { + return Data; + } + const_iterator begin() const { + return Data; + } + iterator end() { return Data + Size(); - } - const_iterator end() const { + } + const_iterator end() const { return Data + Size(); - } + } - pointer data() { - return Data; - } - const_pointer data() const { - return Data; - } + pointer data() { + return Data; + } + const_pointer data() const { + return Data; + } - size_type size() const { + size_type size() const { return Size(); - } - size_type capacity() const { - return *reinterpret_cast<size_type*>(Data - 1); - } + } + size_type capacity() const { + return *reinterpret_cast<size_type*>(Data - 1); + } TBucketDivisor ExtSize() const { return Size; } @@ -302,33 +302,33 @@ public: return +Size.Hint; } - allocator_type get_allocator() const { - return this->_get_alloc(); - } + allocator_type get_allocator() const { + return this->_get_alloc(); + } - const_reference operator[](size_type index) const { + const_reference operator[](size_type index) const { Y_ASSERT(index <= Size()); - return *(Data + index); - } + return *(Data + index); + } - reference operator[](size_type index) { + reference operator[](size_type index) { Y_ASSERT(index <= Size()); - return *(Data + index); - } + return *(Data + index); + } void swap(_yhashtable_buckets& other) { - base_type::swap(other); - DoSwap(Data, other.Data); - DoSwap(Size, other.Size); - } + base_type::swap(other); + DoSwap(Data, other.Data); + DoSwap(Size, other.Size); + } private: - /** Pointer to the first element of the buckets array. */ - pointer Data; + /** Pointer to the first element of the buckets array. */ + pointer Data; - /** Size of the buckets array. Doesn't take the marker element at the end into account. */ + /** Size of the buckets array. Doesn't take the marker element at the end into account. */ TBucketDivisor Size; }; @@ -350,52 +350,52 @@ private: template <class HashFcn, class ExtractKey, class EqualKey, class Alloc, bool IsEmpty = std::is_empty<HashFcn>::value&& std::is_empty<ExtractKey>::value&& std::is_empty<EqualKey>::value> class _yhashtable_base: public _allocator_base<Alloc> { using base_type = _allocator_base<Alloc>; - + public: _yhashtable_base(const HashFcn& hash, const ExtractKey& extract, const EqualKey& equals, const Alloc& alloc) - : base_type(alloc) + : base_type(alloc) , hash_(hash) , extract_(extract) , equals_(equals) - { - } + { + } - const EqualKey& _get_key_eq() const { + const EqualKey& _get_key_eq() const { return equals_; - } - EqualKey& _get_key_eq() { + } + EqualKey& _get_key_eq() { return equals_; - } - void _set_key_eq(const EqualKey& equals) { + } + void _set_key_eq(const EqualKey& equals) { this->equals_ = equals; - } + } - const ExtractKey& _get_key_extract() const { + const ExtractKey& _get_key_extract() const { return extract_; - } - ExtractKey& _get_key_extract() { + } + ExtractKey& _get_key_extract() { return extract_; - } - void _set_key_extract(const ExtractKey& extract) { + } + void _set_key_extract(const ExtractKey& extract) { this->extract_ = extract; - } + } - const HashFcn& _get_hash_fun() const { + const HashFcn& _get_hash_fun() const { return hash_; - } - HashFcn& _get_hash_fun() { + } + HashFcn& _get_hash_fun() { return hash_; - } - void _set_hash_fun(const HashFcn& hash) { + } + void _set_hash_fun(const HashFcn& hash) { this->hash_ = hash; - } + } void swap(_yhashtable_base& other) { - base_type::swap(other); + base_type::swap(other); DoSwap(equals_, other.equals_); DoSwap(extract_, other.extract_); DoSwap(hash_, other.hash_); - } + } private: HashFcn hash_; @@ -403,37 +403,37 @@ private: EqualKey equals_; }; -template <class HashFcn, class ExtractKey, class EqualKey, class Alloc> +template <class HashFcn, class ExtractKey, class EqualKey, class Alloc> class _yhashtable_base<HashFcn, ExtractKey, EqualKey, Alloc, true>: public _allocator_base<Alloc> { using base_type = _allocator_base<Alloc>; public: _yhashtable_base(const HashFcn&, const ExtractKey&, const EqualKey&, const Alloc& alloc) - : base_type(alloc) - { - } - - EqualKey _get_key_eq() const { - return EqualKey(); - } - void _set_key_eq(const EqualKey&) { - } - - ExtractKey _get_key_extract() const { - return ExtractKey(); - } - void _set_key_extract(const ExtractKey&) { - } - - HashFcn _get_hash_fun() const { - return HashFcn(); - } - void _set_hash_fun(const HashFcn&) { - } + : base_type(alloc) + { + } + + EqualKey _get_key_eq() const { + return EqualKey(); + } + void _set_key_eq(const EqualKey&) { + } + + ExtractKey _get_key_extract() const { + return ExtractKey(); + } + void _set_key_extract(const ExtractKey&) { + } + + HashFcn _get_hash_fun() const { + return HashFcn(); + } + void _set_hash_fun(const HashFcn&) { + } void swap(_yhashtable_base& other) { - base_type::swap(other); - } + base_type::swap(other); + } }; template <class Value, class Key, class HashFcn, class ExtractKey, class EqualKey, class Alloc> @@ -473,42 +473,42 @@ public: using reference = value_type&; using const_reference = const value_type&; - node_allocator_type& GetNodeAllocator() { - return this->_get_alloc(); - } - const node_allocator_type& GetNodeAllocator() const { - return this->_get_alloc(); - } - key_equal key_eq() const { - return this->_get_key_eq(); - } + node_allocator_type& GetNodeAllocator() { + return this->_get_alloc(); + } + const node_allocator_type& GetNodeAllocator() const { + return this->_get_alloc(); + } + key_equal key_eq() const { + return this->_get_key_eq(); + } hasher hash_function() const { - return this->_get_hash_fun(); - } + return this->_get_hash_fun(); + } private: - template <class KeyL, class KeyR> - bool equals(const KeyL& l, const KeyR& r) const { - return this->_get_key_eq()(l, r); - } + template <class KeyL, class KeyR> + bool equals(const KeyL& l, const KeyR& r) const { + return this->_get_key_eq()(l, r); + } - /* This method is templated to postpone instantiation of key extraction functor. */ - template <class ValueL> + /* This method is templated to postpone instantiation of key extraction functor. */ + template <class ValueL> auto get_key(const ValueL& value) const -> decltype(ExtractKey()(value)) { - return this->_get_key_extract()(value); - } + return this->_get_key_extract()(value); + } - node* get_node() { + node* get_node() { node* result = this->_get_alloc().allocate(1); Y_ASSERT((reinterpret_cast<uintptr_t>(result) & 1) == 0); /* We're using the last bit of the node pointer. */ return result; - } - void put_node(node* p) { - this->_get_alloc().deallocate(p, 1); - } + } + void put_node(node* p) { + this->_get_alloc().deallocate(p, 1); + } - buckets_type buckets; - size_type num_elements; + buckets_type buckets; + size_type num_elements; public: using iterator = __yhashtable_iterator<Value>; @@ -520,66 +520,66 @@ public: public: THashTable() - : base_type(HashFcn(), ExtractKey(), EqualKey(), node_allocator_type()) - , buckets(nodep_allocator_type()) - , num_elements(0) - { - initialize_buckets(buckets, 0); - } + : base_type(HashFcn(), ExtractKey(), EqualKey(), node_allocator_type()) + , buckets(nodep_allocator_type()) + , num_elements(0) + { + initialize_buckets(buckets, 0); + } THashTable(size_type n, const HashFcn& hf, const EqualKey& eql, const ExtractKey& ext) - : base_type(hf, ext, eql, node_allocator_type()) - , buckets(nodep_allocator_type()) - , num_elements(0) - { - initialize_buckets(buckets, n); - } + : base_type(hf, ext, eql, node_allocator_type()) + , buckets(nodep_allocator_type()) + , num_elements(0) + { + initialize_buckets(buckets, n); + } THashTable(size_type n, const HashFcn& hf, const EqualKey& eql) - : base_type(hf, ExtractKey(), eql, node_allocator_type()) - , buckets(nodep_allocator_type()) - , num_elements(0) - { - initialize_buckets(buckets, n); - } - - template <class TAllocParam> + : base_type(hf, ExtractKey(), eql, node_allocator_type()) + , buckets(nodep_allocator_type()) + , num_elements(0) + { + initialize_buckets(buckets, n); + } + + template <class TAllocParam> THashTable(size_type n, const HashFcn& hf, const EqualKey& eql, TAllocParam* allocParam) - : base_type(hf, ExtractKey(), eql, allocParam) - , buckets(allocParam) - , num_elements(0) - { - initialize_buckets(buckets, n); + : base_type(hf, ExtractKey(), eql, allocParam) + , buckets(allocParam) + , num_elements(0) + { + initialize_buckets(buckets, n); } THashTable(const THashTable& ht) - : base_type(ht._get_hash_fun(), ht._get_key_extract(), ht._get_key_eq(), ht._get_alloc()) - , buckets(ht.buckets.get_allocator()) - , num_elements(0) - { - if (ht.empty()) { - initialize_buckets(buckets, 0); + : base_type(ht._get_hash_fun(), ht._get_key_extract(), ht._get_key_eq(), ht._get_alloc()) + , buckets(ht.buckets.get_allocator()) + , num_elements(0) + { + if (ht.empty()) { + initialize_buckets(buckets, 0); } else { initialize_buckets_dynamic(buckets, ht.buckets.ExtSize()); - copy_from_dynamic(ht); + copy_from_dynamic(ht); } - } + } THashTable(THashTable&& ht) noexcept - : base_type(ht._get_hash_fun(), ht._get_key_extract(), ht._get_key_eq(), ht._get_alloc()) - , buckets(ht.buckets.get_allocator()) - , num_elements(0) - { - initialize_buckets(buckets, 0); - this->swap(ht); + : base_type(ht._get_hash_fun(), ht._get_key_extract(), ht._get_key_eq(), ht._get_alloc()) + , buckets(ht.buckets.get_allocator()) + , num_elements(0) + { + initialize_buckets(buckets, 0); + this->swap(ht); } THashTable& operator=(const THashTable& ht) { - if (&ht != this) { - basic_clear(); - this->_set_hash_fun(ht._get_hash_fun()); - this->_set_key_eq(ht._get_key_eq()); - this->_set_key_extract(ht._get_key_extract()); + if (&ht != this) { + basic_clear(); + this->_set_hash_fun(ht._get_hash_fun()); + this->_set_key_eq(ht._get_key_eq()); + this->_set_key_extract(ht._get_key_extract()); /* We don't copy allocator for a reason. */ if (ht.empty()) { @@ -590,237 +590,237 @@ public: deinitialize_buckets(buckets); initialize_buckets(buckets, 0); } else { - if (buckets.capacity() > ht.buckets.size()) { + if (buckets.capacity() > ht.buckets.size()) { buckets.resize_noallocate(ht.buckets.ExtSize()); - } else { - deinitialize_buckets(buckets); + } else { + deinitialize_buckets(buckets); initialize_buckets_dynamic(buckets, ht.buckets.ExtSize()); - } + } - copy_from_dynamic(ht); - } - } - return *this; - } + copy_from_dynamic(ht); + } + } + return *this; + } THashTable& operator=(THashTable&& ht) noexcept { basic_clear(); swap(ht); - return *this; - } + return *this; + } ~THashTable() { - basic_clear(); - deinitialize_buckets(buckets); - } + basic_clear(); + deinitialize_buckets(buckets); + } size_type size() const noexcept { - return num_elements; - } + return num_elements; + } size_type max_size() const noexcept { - return size_type(-1); - } + return size_type(-1); + } - Y_PURE_FUNCTION bool empty() const noexcept { - return size() == 0; - } + Y_PURE_FUNCTION bool empty() const noexcept { + return size() == 0; + } void swap(THashTable& ht) { - base_type::swap(ht); - buckets.swap(ht.buckets); - DoSwap(num_elements, ht.num_elements); - } - - iterator begin() { - for (size_type n = 0; n < buckets.size(); ++n) /*y*/ - if (buckets[n]) - return iterator(buckets[n]); /*y*/ - return end(); - } - - iterator end() { + base_type::swap(ht); + buckets.swap(ht.buckets); + DoSwap(num_elements, ht.num_elements); + } + + iterator begin() { + for (size_type n = 0; n < buckets.size(); ++n) /*y*/ + if (buckets[n]) + return iterator(buckets[n]); /*y*/ + return end(); + } + + iterator end() { return iterator(nullptr); - } /*y*/ - - const_iterator begin() const { - for (size_type n = 0; n < buckets.size(); ++n) /*y*/ - if (buckets[n]) - return const_iterator(buckets[n]); /*y*/ - return end(); - } - - const_iterator end() const { + } /*y*/ + + const_iterator begin() const { + for (size_type n = 0; n < buckets.size(); ++n) /*y*/ + if (buckets[n]) + return const_iterator(buckets[n]); /*y*/ + return end(); + } + + const_iterator end() const { return const_iterator(nullptr); - } /*y*/ - + } /*y*/ + public: - size_type bucket_count() const { - return buckets.size(); - } /*y*/ + size_type bucket_count() const { + return buckets.size(); + } /*y*/ size_type bucket_size(size_type bucket) const { - size_type result = 0; - if (const node* cur = buckets[bucket]) - for (; !((uintptr_t)cur & 1); cur = cur->next) - result += 1; - return result; - } - - template <class OtherValue> + size_type result = 0; + if (const node* cur = buckets[bucket]) + for (; !((uintptr_t)cur & 1); cur = cur->next) + result += 1; + return result; + } + + template <class OtherValue> std::pair<iterator, bool> insert_unique(const OtherValue& obj) { reserve(num_elements + 1); - return insert_unique_noresize(obj); - } + return insert_unique_noresize(obj); + } - template <class OtherValue> + template <class OtherValue> iterator insert_equal(const OtherValue& obj) { reserve(num_elements + 1); return emplace_equal_noresize(obj); - } + } template <typename... Args> - iterator emplace_equal(Args&&... args) { + iterator emplace_equal(Args&&... args) { reserve(num_elements + 1); return emplace_equal_noresize(std::forward<Args>(args)...); } - template <class OtherValue> + template <class OtherValue> iterator insert_direct(const OtherValue& obj, insert_ctx ins) { return emplace_direct(ins, obj); } template <typename... Args> - iterator emplace_direct(insert_ctx ins, Args&&... args) { + iterator emplace_direct(insert_ctx ins, Args&&... args) { bool resized = reserve(num_elements + 1); node* tmp = new_node(std::forward<Args>(args)...); - if (resized) { - find_i(get_key(tmp->val), ins); - } - tmp->next = *ins ? *ins : (node*)((uintptr_t)(ins + 1) | 1); - *ins = tmp; - ++num_elements; - return iterator(tmp); + if (resized) { + find_i(get_key(tmp->val), ins); + } + tmp->next = *ins ? *ins : (node*)((uintptr_t)(ins + 1) | 1); + *ins = tmp; + ++num_elements; + return iterator(tmp); } template <typename... Args> - std::pair<iterator, bool> emplace_unique(Args&&... args) { + std::pair<iterator, bool> emplace_unique(Args&&... args) { reserve(num_elements + 1); return emplace_unique_noresize(std::forward<Args>(args)...); } template <typename... Args> - std::pair<iterator, bool> emplace_unique_noresize(Args&&... args); + std::pair<iterator, bool> emplace_unique_noresize(Args&&... args); template <class OtherValue> std::pair<iterator, bool> insert_unique_noresize(const OtherValue& obj); template <typename... Args> - iterator emplace_equal_noresize(Args&&... args); - - template <class InputIterator> - void insert_unique(InputIterator f, InputIterator l) { - insert_unique(f, l, typename std::iterator_traits<InputIterator>::iterator_category()); - } - - template <class InputIterator> - void insert_equal(InputIterator f, InputIterator l) { - insert_equal(f, l, typename std::iterator_traits<InputIterator>::iterator_category()); - } - - template <class InputIterator> - void insert_unique(InputIterator f, InputIterator l, std::input_iterator_tag) { - for (; f != l; ++f) - insert_unique(*f); - } - - template <class InputIterator> - void insert_equal(InputIterator f, InputIterator l, std::input_iterator_tag) { - for (; f != l; ++f) - insert_equal(*f); - } - - template <class ForwardIterator> - void insert_unique(ForwardIterator f, ForwardIterator l, std::forward_iterator_tag) { - difference_type n = std::distance(f, l); + iterator emplace_equal_noresize(Args&&... args); + + template <class InputIterator> + void insert_unique(InputIterator f, InputIterator l) { + insert_unique(f, l, typename std::iterator_traits<InputIterator>::iterator_category()); + } + + template <class InputIterator> + void insert_equal(InputIterator f, InputIterator l) { + insert_equal(f, l, typename std::iterator_traits<InputIterator>::iterator_category()); + } + + template <class InputIterator> + void insert_unique(InputIterator f, InputIterator l, std::input_iterator_tag) { + for (; f != l; ++f) + insert_unique(*f); + } + + template <class InputIterator> + void insert_equal(InputIterator f, InputIterator l, std::input_iterator_tag) { + for (; f != l; ++f) + insert_equal(*f); + } + + template <class ForwardIterator> + void insert_unique(ForwardIterator f, ForwardIterator l, std::forward_iterator_tag) { + difference_type n = std::distance(f, l); reserve(num_elements + n); - for (; n > 0; --n, ++f) - insert_unique_noresize(*f); - } + for (; n > 0; --n, ++f) + insert_unique_noresize(*f); + } - template <class ForwardIterator> - void insert_equal(ForwardIterator f, ForwardIterator l, std::forward_iterator_tag) { - difference_type n = std::distance(f, l); + template <class ForwardIterator> + void insert_equal(ForwardIterator f, ForwardIterator l, std::forward_iterator_tag) { + difference_type n = std::distance(f, l); reserve(num_elements + n); - for (; n > 0; --n, ++f) + for (; n > 0; --n, ++f) emplace_equal_noresize(*f); - } + } - template <class OtherValue> + template <class OtherValue> reference find_or_insert(const OtherValue& v); - template <class OtherKey> + template <class OtherKey> iterator find(const OtherKey& key) { - size_type n = bkt_num_key(key); - node* first; - for (first = buckets[n]; - first && !equals(get_key(first->val), key); + size_type n = bkt_num_key(key); + node* first; + for (first = buckets[n]; + first && !equals(get_key(first->val), key); first = ((uintptr_t)first->next & 1) ? nullptr : first->next) /*y*/ - { - } - return iterator(first); /*y*/ - } - - template <class OtherKey> + { + } + return iterator(first); /*y*/ + } + + template <class OtherKey> const_iterator find(const OtherKey& key) const { - size_type n = bkt_num_key(key); - const node* first; - for (first = buckets[n]; - first && !equals(get_key(first->val), key); + size_type n = bkt_num_key(key); + const node* first; + for (first = buckets[n]; + first && !equals(get_key(first->val), key); first = ((uintptr_t)first->next & 1) ? nullptr : first->next) /*y*/ - { - } - return const_iterator(first); /*y*/ - } + { + } + return const_iterator(first); /*y*/ + } - template <class OtherKey> + template <class OtherKey> iterator find_i(const OtherKey& key, insert_ctx& ins); - template <class OtherKey> + template <class OtherKey> size_type count(const OtherKey& key) const { - const size_type n = bkt_num_key(key); - size_type result = 0; + const size_type n = bkt_num_key(key); + size_type result = 0; - if (const node* cur = buckets[n]) - for (; !((uintptr_t)cur & 1); cur = cur->next) - if (equals(get_key(cur->val), key)) - ++result; - return result; - } + if (const node* cur = buckets[n]) + for (; !((uintptr_t)cur & 1); cur = cur->next) + if (equals(get_key(cur->val), key)) + ++result; + return result; + } - template <class OtherKey> + template <class OtherKey> std::pair<iterator, iterator> equal_range(const OtherKey& key); - template <class OtherKey> + template <class OtherKey> std::pair<const_iterator, const_iterator> equal_range(const OtherKey& key) const; - template <class OtherKey> + template <class OtherKey> size_type erase(const OtherKey& key); - template <class OtherKey> + template <class OtherKey> size_type erase_one(const OtherKey& key); // void (instead of iterator) is intended, see http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2006/n2023.pdf - void erase(const iterator& it); - void erase(iterator first, iterator last); + void erase(const iterator& it); + void erase(iterator first, iterator last); - void erase(const const_iterator& it); - void erase(const_iterator first, const_iterator last); + void erase(const const_iterator& it); + void erase(const_iterator first, const_iterator last); bool reserve(size_type num_elements_hint); - void basic_clear(); + void basic_clear(); /** * Clears the hashtable without deallocating the nodes. @@ -837,119 +837,119 @@ public: num_elements = 0; } - // implemented in save_stl.h - template <class KeySaver> + // implemented in save_stl.h + template <class KeySaver> int save_for_st(IOutputStream* stream, KeySaver& ks, sthash<int, int, THash<int>, TEqualTo<int>, typename KeySaver::TSizeType>* stHash = nullptr) const; - void clear(size_type downsize) { - basic_clear(); + void clear(size_type downsize) { + basic_clear(); - if (downsize < buckets.size()) { + if (downsize < buckets.size()) { const TBucketDivisor newSize = HashBucketCountExt(downsize); if (newSize() < buckets.size()) { Y_ASSERT(newSize() >= 7); /* We cannot downsize static buckets. */ buckets.resize_noallocate(newSize); - } - } - } - - /** - * Clears the hashtable and tries to reasonably downsize it. Note that - * downsizing is mainly for the following use case: - * + } + } + } + + /** + * Clears the hashtable and tries to reasonably downsize it. Note that + * downsizing is mainly for the following use case: + * * THashTable hash; - * for(...) { - * if (someCond()) - * hash.clear(); - * hash.insert(...); - * } - * - * Here if at some point `hash` gets really big, then all the following calls - * to `clear` become really slow as they have to iterate through all the the - * empty buckets. This is worked around by squeezing the buckets array a little - * bit with every `clear` call. - * - * Alternatively, the user can call `basic_clear`, which doesn't do the - * downsizing. - */ - void clear() { - if (num_elements) - clear((num_elements * 2 + buckets.size()) / 3); + * for(...) { + * if (someCond()) + * hash.clear(); + * hash.insert(...); + * } + * + * Here if at some point `hash` gets really big, then all the following calls + * to `clear` become really slow as they have to iterate through all the the + * empty buckets. This is worked around by squeezing the buckets array a little + * bit with every `clear` call. + * + * Alternatively, the user can call `basic_clear`, which doesn't do the + * downsizing. + */ + void clear() { + if (num_elements) + clear((num_elements * 2 + buckets.size()) / 3); } private: - static void initialize_buckets(buckets_type& buckets, size_type sizeHint) { - if (sizeHint == 0) { + static void initialize_buckets(buckets_type& buckets, size_type sizeHint) { + if (sizeHint == 0) { buckets.initialize_static(reinterpret_cast<node**>(const_cast<void**>(_yhashtable_empty_data)) + 1, TBucketDivisor::One()); - } else { + } else { TBucketDivisor size = HashBucketCountExt(sizeHint); Y_ASSERT(size() >= 7); - initialize_buckets_dynamic(buckets, size); - } + initialize_buckets_dynamic(buckets, size); + } } static void initialize_buckets_dynamic(buckets_type& buckets, TBucketDivisor size) { - buckets.initialize_dynamic(size); + buckets.initialize_dynamic(size); memset(buckets.data(), 0, size() * sizeof(*buckets.data())); buckets[size()] = (node*)1; - } + } - static void deinitialize_buckets(buckets_type& buckets) { - if (buckets.size() == 1) { - buckets.deinitialize_static(); - } else { - buckets.deinitialize_dynamic(); - } + static void deinitialize_buckets(buckets_type& buckets) { + if (buckets.size() == 1) { + buckets.deinitialize_static(); + } else { + buckets.deinitialize_dynamic(); + } } - static void clear_buckets(buckets_type& buckets) { - memset(buckets.data(), 0, buckets.size() * sizeof(*buckets.data())); - } + static void clear_buckets(buckets_type& buckets) { + memset(buckets.data(), 0, buckets.size() * sizeof(*buckets.data())); + } - template <class OtherKey> + template <class OtherKey> size_type bkt_num_key(const OtherKey& key) const { return bkt_num_key(key, buckets.ExtSize()); - } + } - template <class OtherValue> + template <class OtherValue> size_type bkt_num(const OtherValue& obj) const { - return bkt_num_key(get_key(obj)); - } + return bkt_num_key(get_key(obj)); + } - template <class OtherKey> + template <class OtherKey> size_type bkt_num_key(const OtherKey& key, TBucketDivisor n) const { const size_type bucket = n.Remainder(this->_get_hash_fun()(key)); Y_ASSERT((0 <= bucket) && (bucket < n())); return bucket; - } + } - template <class OtherValue> + template <class OtherValue> size_type bkt_num(const OtherValue& obj, TBucketDivisor n) const { - return bkt_num_key(get_key(obj), n); - } + return bkt_num_key(get_key(obj), n); + } template <typename... Args> - node* new_node(Args&&... val) { - node* n = get_node(); - n->next = (node*)1; /*y*/ // just for a case - try { + node* new_node(Args&&... val) { + node* n = get_node(); + n->next = (node*)1; /*y*/ // just for a case + try { new (static_cast<void*>(&n->val)) Value(std::forward<Args>(val)...); - } catch (...) { - put_node(n); - throw; - } - return n; - } - - void delete_node(node* n) { - n->val.~Value(); - //n->next = (node*) 0xDeadBeeful; + } catch (...) { + put_node(n); + throw; + } + return n; + } + + void delete_node(node* n) { + n->val.~Value(); + //n->next = (node*) 0xDeadBeeful; put_node(n); } - void erase_bucket(const size_type n, node* first, node* last); - void erase_bucket(const size_type n, node* last); + void erase_bucket(const size_type n, node* first, node* last); + void erase_bucket(const size_type n, node* last); void copy_from_dynamic(const THashTable& ht); }; @@ -959,7 +959,7 @@ __yhashtable_iterator<V>& __yhashtable_iterator<V>::operator++() { Y_ASSERT(cur); cur = cur->next; if ((uintptr_t)cur & 1) { - node** bucket = (node**)((uintptr_t)cur & ~1); + node** bucket = (node**)((uintptr_t)cur & ~1); while (*bucket == nullptr) ++bucket; Y_ASSERT(*bucket != nullptr); @@ -970,9 +970,9 @@ __yhashtable_iterator<V>& __yhashtable_iterator<V>::operator++() { template <class V> inline __yhashtable_iterator<V> __yhashtable_iterator<V>::operator++(int) { - iterator tmp = *this; - ++*this; - return tmp; + iterator tmp = *this; + ++*this; + return tmp; } template <class V> @@ -980,7 +980,7 @@ __yhashtable_const_iterator<V>& __yhashtable_const_iterator<V>::operator++() { Y_ASSERT(cur); cur = cur->next; if ((uintptr_t)cur & 1) { - node** bucket = (node**)((uintptr_t)cur & ~1); + node** bucket = (node**)((uintptr_t)cur & ~1); while (*bucket == nullptr) ++bucket; Y_ASSERT(*bucket != nullptr); @@ -991,15 +991,15 @@ __yhashtable_const_iterator<V>& __yhashtable_const_iterator<V>::operator++() { template <class V> inline __yhashtable_const_iterator<V> __yhashtable_const_iterator<V>::operator++(int) { - const_iterator tmp = *this; - ++*this; - return tmp; + const_iterator tmp = *this; + ++*this; + return tmp; } template <class V, class K, class HF, class Ex, class Eq, class A> template <typename... Args> std::pair<typename THashTable<V, K, HF, Ex, Eq, A>::iterator, bool> THashTable<V, K, HF, Ex, Eq, A>::emplace_unique_noresize(Args&&... args) { - auto deleter = [&](node* tmp) { delete_node(tmp); }; + auto deleter = [&](node* tmp) { delete_node(tmp); }; node* tmp = new_node(std::forward<Args>(args)...); std::unique_ptr<node, decltype(deleter)> guard(tmp, deleter); @@ -1021,45 +1021,45 @@ std::pair<typename THashTable<V, K, HF, Ex, Eq, A>::iterator, bool> THashTable<V template <class V, class K, class HF, class Ex, class Eq, class A> template <class OtherValue> std::pair<typename THashTable<V, K, HF, Ex, Eq, A>::iterator, bool> THashTable<V, K, HF, Ex, Eq, A>::insert_unique_noresize(const OtherValue& obj) { - const size_type n = bkt_num(obj); - node* first = buckets[n]; + const size_type n = bkt_num(obj); + node* first = buckets[n]; - if (first) /*y*/ - for (node* cur = first; !((uintptr_t)cur & 1); cur = cur->next) /*y*/ - if (equals(get_key(cur->val), get_key(obj))) + if (first) /*y*/ + for (node* cur = first; !((uintptr_t)cur & 1); cur = cur->next) /*y*/ + if (equals(get_key(cur->val), get_key(obj))) return std::pair<iterator, bool>(iterator(cur), false); /*y*/ - node* tmp = new_node(obj); - tmp->next = first ? first : (node*)((uintptr_t)&buckets[n + 1] | 1); /*y*/ - buckets[n] = tmp; - ++num_elements; + node* tmp = new_node(obj); + tmp->next = first ? first : (node*)((uintptr_t)&buckets[n + 1] | 1); /*y*/ + buckets[n] = tmp; + ++num_elements; return std::pair<iterator, bool>(iterator(tmp), true); /*y*/ } template <class V, class K, class HF, class Ex, class Eq, class A> template <typename... Args> __yhashtable_iterator<V> THashTable<V, K, HF, Ex, Eq, A>::emplace_equal_noresize(Args&&... args) { - auto deleter = [&](node* tmp) { delete_node(tmp); }; + auto deleter = [&](node* tmp) { delete_node(tmp); }; node* tmp = new_node(std::forward<Args>(args)...); std::unique_ptr<node, decltype(deleter)> guard(tmp, deleter); const size_type n = bkt_num(tmp->val); - node* first = buckets[n]; + node* first = buckets[n]; - if (first) /*y*/ - for (node* cur = first; !((uintptr_t)cur & 1); cur = cur->next) /*y*/ + if (first) /*y*/ + for (node* cur = first; !((uintptr_t)cur & 1); cur = cur->next) /*y*/ if (equals(get_key(cur->val), get_key(tmp->val))) { guard.release(); - tmp->next = cur->next; - cur->next = tmp; - ++num_elements; - return iterator(tmp); /*y*/ - } + tmp->next = cur->next; + cur->next = tmp; + ++num_elements; + return iterator(tmp); /*y*/ + } guard.release(); - tmp->next = first ? first : (node*)((uintptr_t)&buckets[n + 1] | 1); /*y*/ - buckets[n] = tmp; - ++num_elements; - return iterator(tmp); /*y*/ + tmp->next = first ? first : (node*)((uintptr_t)&buckets[n + 1] | 1); /*y*/ + buckets[n] = tmp; + ++num_elements; + return iterator(tmp); /*y*/ } template <class V, class K, class HF, class Ex, class Eq, class A> @@ -1067,327 +1067,327 @@ template <class OtherValue> typename THashTable<V, K, HF, Ex, Eq, A>::reference THashTable<V, K, HF, Ex, Eq, A>::find_or_insert(const OtherValue& v) { reserve(num_elements + 1); - size_type n = bkt_num_key(get_key(v)); - node* first = buckets[n]; + size_type n = bkt_num_key(get_key(v)); + node* first = buckets[n]; - if (first) /*y*/ - for (node* cur = first; !((uintptr_t)cur & 1); cur = cur->next) /*y*/ - if (equals(get_key(cur->val), get_key(v))) - return cur->val; + if (first) /*y*/ + for (node* cur = first; !((uintptr_t)cur & 1); cur = cur->next) /*y*/ + if (equals(get_key(cur->val), get_key(v))) + return cur->val; - node* tmp = new_node(v); - tmp->next = first ? first : (node*)((uintptr_t)&buckets[n + 1] | 1); /*y*/ - buckets[n] = tmp; - ++num_elements; - return tmp->val; + node* tmp = new_node(v); + tmp->next = first ? first : (node*)((uintptr_t)&buckets[n + 1] | 1); /*y*/ + buckets[n] = tmp; + ++num_elements; + return tmp->val; } template <class V, class K, class HF, class Ex, class Eq, class A> template <class OtherKey> __yhashtable_iterator<V> THashTable<V, K, HF, Ex, Eq, A>::find_i(const OtherKey& key, insert_ctx& ins) { - size_type n = bkt_num_key(key); - ins = &buckets[n]; - node* first = buckets[n]; - - if (first) /*y*/ - for (node* cur = first; !((uintptr_t)cur & 1); cur = cur->next) /*y*/ - if (equals(get_key(cur->val), key)) - return iterator(cur); /*y*/ - return end(); + size_type n = bkt_num_key(key); + ins = &buckets[n]; + node* first = buckets[n]; + + if (first) /*y*/ + for (node* cur = first; !((uintptr_t)cur & 1); cur = cur->next) /*y*/ + if (equals(get_key(cur->val), key)) + return iterator(cur); /*y*/ + return end(); } template <class V, class K, class HF, class Ex, class Eq, class A> template <class OtherKey> std::pair<__yhashtable_iterator<V>, __yhashtable_iterator<V>> THashTable<V, K, HF, Ex, Eq, A>::equal_range(const OtherKey& key) { using pii = std::pair<iterator, iterator>; - const size_type n = bkt_num_key(key); - node* first = buckets[n]; - - if (first) /*y*/ - for (; !((uintptr_t)first & 1); first = first->next) { /*y*/ - if (equals(get_key(first->val), key)) { - for (node* cur = first->next; !((uintptr_t)cur & 1); cur = cur->next) - if (!equals(get_key(cur->val), key)) - return pii(iterator(first), iterator(cur)); /*y*/ - for (size_type m = n + 1; m < buckets.size(); ++m) /*y*/ - if (buckets[m]) - return pii(iterator(first), /*y*/ - iterator(buckets[m])); /*y*/ - return pii(iterator(first), end()); /*y*/ - } - } - return pii(end(), end()); + const size_type n = bkt_num_key(key); + node* first = buckets[n]; + + if (first) /*y*/ + for (; !((uintptr_t)first & 1); first = first->next) { /*y*/ + if (equals(get_key(first->val), key)) { + for (node* cur = first->next; !((uintptr_t)cur & 1); cur = cur->next) + if (!equals(get_key(cur->val), key)) + return pii(iterator(first), iterator(cur)); /*y*/ + for (size_type m = n + 1; m < buckets.size(); ++m) /*y*/ + if (buckets[m]) + return pii(iterator(first), /*y*/ + iterator(buckets[m])); /*y*/ + return pii(iterator(first), end()); /*y*/ + } + } + return pii(end(), end()); } template <class V, class K, class HF, class Ex, class Eq, class A> template <class OtherKey> std::pair<__yhashtable_const_iterator<V>, __yhashtable_const_iterator<V>> THashTable<V, K, HF, Ex, Eq, A>::equal_range(const OtherKey& key) const { using pii = std::pair<const_iterator, const_iterator>; - const size_type n = bkt_num_key(key); - const node* first = buckets[n]; - - if (first) /*y*/ - for (; !((uintptr_t)first & 1); first = first->next) { /*y*/ - if (equals(get_key(first->val), key)) { - for (const node* cur = first->next; !((uintptr_t)cur & 1); cur = cur->next) - if (!equals(get_key(cur->val), key)) - return pii(const_iterator(first), /*y*/ - const_iterator(cur)); /*y*/ - for (size_type m = n + 1; m < buckets.size(); ++m) /*y*/ - if (buckets[m]) - return pii(const_iterator(first /*y*/), - const_iterator(buckets[m] /*y*/)); - return pii(const_iterator(first /*y*/), end()); - } - } - return pii(end(), end()); + const size_type n = bkt_num_key(key); + const node* first = buckets[n]; + + if (first) /*y*/ + for (; !((uintptr_t)first & 1); first = first->next) { /*y*/ + if (equals(get_key(first->val), key)) { + for (const node* cur = first->next; !((uintptr_t)cur & 1); cur = cur->next) + if (!equals(get_key(cur->val), key)) + return pii(const_iterator(first), /*y*/ + const_iterator(cur)); /*y*/ + for (size_type m = n + 1; m < buckets.size(); ++m) /*y*/ + if (buckets[m]) + return pii(const_iterator(first /*y*/), + const_iterator(buckets[m] /*y*/)); + return pii(const_iterator(first /*y*/), end()); + } + } + return pii(end(), end()); } template <class V, class K, class HF, class Ex, class Eq, class A> template <class OtherKey> typename THashTable<V, K, HF, Ex, Eq, A>::size_type THashTable<V, K, HF, Ex, Eq, A>::erase(const OtherKey& key) { - const size_type n = bkt_num_key(key); - node* first = buckets[n]; - size_type erased = 0; - - if (first) { - node* cur = first; - node* next = cur->next; - while (!((uintptr_t)next & 1)) { /*y*/ - if (equals(get_key(next->val), key)) { - cur->next = next->next; - ++erased; - --num_elements; - delete_node(next); - next = cur->next; - } else { - cur = next; - next = cur->next; - } - } - if (equals(get_key(first->val), key)) { + const size_type n = bkt_num_key(key); + node* first = buckets[n]; + size_type erased = 0; + + if (first) { + node* cur = first; + node* next = cur->next; + while (!((uintptr_t)next & 1)) { /*y*/ + if (equals(get_key(next->val), key)) { + cur->next = next->next; + ++erased; + --num_elements; + delete_node(next); + next = cur->next; + } else { + cur = next; + next = cur->next; + } + } + if (equals(get_key(first->val), key)) { buckets[n] = ((uintptr_t)first->next & 1) ? nullptr : first->next; /*y*/ - ++erased; - --num_elements; - delete_node(first); - } + ++erased; + --num_elements; + delete_node(first); + } } - return erased; + return erased; } template <class V, class K, class HF, class Ex, class Eq, class A> template <class OtherKey> typename THashTable<V, K, HF, Ex, Eq, A>::size_type THashTable<V, K, HF, Ex, Eq, A>::erase_one(const OtherKey& key) { - const size_type n = bkt_num_key(key); - node* first = buckets[n]; - - if (first) { - node* cur = first; - node* next = cur->next; - while (!((uintptr_t)next & 1)) { /*y*/ - if (equals(get_key(next->val), key)) { - cur->next = next->next; - --num_elements; - delete_node(next); - return 1; - } else { - cur = next; - next = cur->next; - } - } - if (equals(get_key(first->val), key)) { + const size_type n = bkt_num_key(key); + node* first = buckets[n]; + + if (first) { + node* cur = first; + node* next = cur->next; + while (!((uintptr_t)next & 1)) { /*y*/ + if (equals(get_key(next->val), key)) { + cur->next = next->next; + --num_elements; + delete_node(next); + return 1; + } else { + cur = next; + next = cur->next; + } + } + if (equals(get_key(first->val), key)) { buckets[n] = ((uintptr_t)first->next & 1) ? nullptr : first->next; /*y*/ - --num_elements; - delete_node(first); - return 1; - } + --num_elements; + delete_node(first); + return 1; + } } - return 0; + return 0; } template <class V, class K, class HF, class Ex, class Eq, class A> void THashTable<V, K, HF, Ex, Eq, A>::erase(const iterator& it) { - if (node* const p = it.cur) { - const size_type n = bkt_num(p->val); - node* cur = buckets[n]; + if (node* const p = it.cur) { + const size_type n = bkt_num(p->val); + node* cur = buckets[n]; - if (cur == p) { + if (cur == p) { buckets[n] = ((uintptr_t)cur->next & 1) ? nullptr : cur->next; /*y*/ - delete_node(cur); - --num_elements; - } else { - node* next = cur->next; - while (!((uintptr_t)next & 1)) { - if (next == p) { - cur->next = next->next; - delete_node(next); - --num_elements; - break; - } else { - cur = next; - next = cur->next; - } - } + delete_node(cur); + --num_elements; + } else { + node* next = cur->next; + while (!((uintptr_t)next & 1)) { + if (next == p) { + cur->next = next->next; + delete_node(next); + --num_elements; + break; + } else { + cur = next; + next = cur->next; + } + } } } } template <class V, class K, class HF, class Ex, class Eq, class A> void THashTable<V, K, HF, Ex, Eq, A>::erase(iterator first, iterator last) { - size_type f_bucket = first.cur ? bkt_num(first.cur->val) : buckets.size(); /*y*/ - size_type l_bucket = last.cur ? bkt_num(last.cur->val) : buckets.size(); /*y*/ - - if (first.cur == last.cur) - return; - else if (f_bucket == l_bucket) - erase_bucket(f_bucket, first.cur, last.cur); - else { + size_type f_bucket = first.cur ? bkt_num(first.cur->val) : buckets.size(); /*y*/ + size_type l_bucket = last.cur ? bkt_num(last.cur->val) : buckets.size(); /*y*/ + + if (first.cur == last.cur) + return; + else if (f_bucket == l_bucket) + erase_bucket(f_bucket, first.cur, last.cur); + else { erase_bucket(f_bucket, first.cur, nullptr); - for (size_type n = f_bucket + 1; n < l_bucket; ++n) + for (size_type n = f_bucket + 1; n < l_bucket; ++n) erase_bucket(n, nullptr); - if (l_bucket != buckets.size()) /*y*/ - erase_bucket(l_bucket, last.cur); - } + if (l_bucket != buckets.size()) /*y*/ + erase_bucket(l_bucket, last.cur); + } } template <class V, class K, class HF, class Ex, class Eq, class A> inline void THashTable<V, K, HF, Ex, Eq, A>::erase(const_iterator first, const_iterator last) { - erase(iterator(const_cast<node*>(first.cur)), iterator(const_cast<node*>(last.cur))); + erase(iterator(const_cast<node*>(first.cur)), iterator(const_cast<node*>(last.cur))); } template <class V, class K, class HF, class Ex, class Eq, class A> inline void THashTable<V, K, HF, Ex, Eq, A>::erase(const const_iterator& it) { - erase(iterator(const_cast<node*>(it.cur))); + erase(iterator(const_cast<node*>(it.cur))); } template <class V, class K, class HF, class Ex, class Eq, class A> bool THashTable<V, K, HF, Ex, Eq, A>::reserve(size_type num_elements_hint) { - const size_type old_n = buckets.size(); /*y*/ - if (num_elements_hint + 1 > old_n) { + const size_type old_n = buckets.size(); /*y*/ + if (num_elements_hint + 1 > old_n) { if (old_n != 1 && num_elements_hint <= old_n) // TODO: this if is for backwards compatibility down to order-in-buckets level. Can be safely removed. return false; const TBucketDivisor n = HashBucketCountExt(num_elements_hint + 1, buckets.BucketDivisorHint() + 1); if (n() > old_n) { - buckets_type tmp(buckets.get_allocator()); - initialize_buckets_dynamic(tmp, n); -#ifdef __STL_USE_EXCEPTIONS - try { -#endif /* __STL_USE_EXCEPTIONS */ - for (size_type bucket = 0; bucket < old_n; ++bucket) { - node* first = buckets[bucket]; - while (first) { - size_type new_bucket = bkt_num(first->val, n); - node* next = first->next; + buckets_type tmp(buckets.get_allocator()); + initialize_buckets_dynamic(tmp, n); +#ifdef __STL_USE_EXCEPTIONS + try { +#endif /* __STL_USE_EXCEPTIONS */ + for (size_type bucket = 0; bucket < old_n; ++bucket) { + node* first = buckets[bucket]; + while (first) { + size_type new_bucket = bkt_num(first->val, n); + node* next = first->next; buckets[bucket] = ((uintptr_t)next & 1) ? nullptr : next; /*y*/ - next = tmp[new_bucket]; - first->next = next ? next : (node*)((uintptr_t) & (tmp[new_bucket + 1]) | 1); /*y*/ - tmp[new_bucket] = first; - first = buckets[bucket]; - } - } - - buckets.swap(tmp); - deinitialize_buckets(tmp); - - return true; -#ifdef __STL_USE_EXCEPTIONS - } catch (...) { - for (size_type bucket = 0; bucket < tmp.size() - 1; ++bucket) { - while (tmp[bucket]) { - node* next = tmp[bucket]->next; - delete_node(tmp[bucket]); + next = tmp[new_bucket]; + first->next = next ? next : (node*)((uintptr_t) & (tmp[new_bucket + 1]) | 1); /*y*/ + tmp[new_bucket] = first; + first = buckets[bucket]; + } + } + + buckets.swap(tmp); + deinitialize_buckets(tmp); + + return true; +#ifdef __STL_USE_EXCEPTIONS + } catch (...) { + for (size_type bucket = 0; bucket < tmp.size() - 1; ++bucket) { + while (tmp[bucket]) { + node* next = tmp[bucket]->next; + delete_node(tmp[bucket]); tmp[bucket] = ((uintptr_t)next & 1) ? nullptr : next /*y*/; - } - } - throw; - } -#endif /* __STL_USE_EXCEPTIONS */ + } + } + throw; + } +#endif /* __STL_USE_EXCEPTIONS */ } } - - return false; + + return false; } template <class V, class K, class HF, class Ex, class Eq, class A> void THashTable<V, K, HF, Ex, Eq, A>::erase_bucket(const size_type n, node* first, node* last) { - node* cur = buckets[n]; - if (cur == first) - erase_bucket(n, last); - else { - node* next; - for (next = cur->next; next != first; cur = next, next = cur->next) - ; - while (next != last) { /*y; 3.1*/ - cur->next = next->next; - delete_node(next); + node* cur = buckets[n]; + if (cur == first) + erase_bucket(n, last); + else { + node* next; + for (next = cur->next; next != first; cur = next, next = cur->next) + ; + while (next != last) { /*y; 3.1*/ + cur->next = next->next; + delete_node(next); next = ((uintptr_t)cur->next & 1) ? nullptr : cur->next; /*y*/ - --num_elements; - } + --num_elements; + } } } template <class V, class K, class HF, class Ex, class Eq, class A> void THashTable<V, K, HF, Ex, Eq, A>::erase_bucket(const size_type n, node* last) { - node* cur = buckets[n]; - while (cur != last) { - node* next = cur->next; - delete_node(cur); + node* cur = buckets[n]; + while (cur != last) { + node* next = cur->next; + delete_node(cur); cur = ((uintptr_t)next & 1) ? nullptr : next; /*y*/ - buckets[n] = cur; - --num_elements; - } + buckets[n] = cur; + --num_elements; + } } template <class V, class K, class HF, class Ex, class Eq, class A> void THashTable<V, K, HF, Ex, Eq, A>::basic_clear() { - if (!num_elements) { - return; - } - - node** first = buckets.begin(); - node** last = buckets.end(); - for (; first < last; ++first) { - node* cur = *first; - if (cur) { /*y*/ - while (!((uintptr_t)cur & 1)) { /*y*/ - node* next = cur->next; - delete_node(cur); - cur = next; - } + if (!num_elements) { + return; + } + + node** first = buckets.begin(); + node** last = buckets.end(); + for (; first < last; ++first) { + node* cur = *first; + if (cur) { /*y*/ + while (!((uintptr_t)cur & 1)) { /*y*/ + node* next = cur->next; + delete_node(cur); + cur = next; + } *first = nullptr; - } + } } - num_elements = 0; + num_elements = 0; } template <class V, class K, class HF, class Ex, class Eq, class A> void THashTable<V, K, HF, Ex, Eq, A>::copy_from_dynamic(const THashTable& ht) { Y_ASSERT(buckets.size() == ht.buckets.size() && !ht.empty()); -#ifdef __STL_USE_EXCEPTIONS - try { -#endif /* __STL_USE_EXCEPTIONS */ - for (size_type i = 0; i < ht.buckets.size(); ++i) { /*y*/ - if (const node* cur = ht.buckets[i]) { - node* copy = new_node(cur->val); - buckets[i] = copy; - - for (node* next = cur->next; !((uintptr_t)next & 1); cur = next, next = cur->next) { - copy->next = new_node(next->val); - copy = copy->next; - } - copy->next = (node*)((uintptr_t)&buckets[i + 1] | 1); /*y*/ - } +#ifdef __STL_USE_EXCEPTIONS + try { +#endif /* __STL_USE_EXCEPTIONS */ + for (size_type i = 0; i < ht.buckets.size(); ++i) { /*y*/ + if (const node* cur = ht.buckets[i]) { + node* copy = new_node(cur->val); + buckets[i] = copy; + + for (node* next = cur->next; !((uintptr_t)next & 1); cur = next, next = cur->next) { + copy->next = new_node(next->val); + copy = copy->next; + } + copy->next = (node*)((uintptr_t)&buckets[i + 1] | 1); /*y*/ + } } - num_elements = ht.num_elements; -#ifdef __STL_USE_EXCEPTIONS - } catch (...) { - basic_clear(); - throw; + num_elements = ht.num_elements; +#ifdef __STL_USE_EXCEPTIONS + } catch (...) { + basic_clear(); + throw; } -#endif /* __STL_USE_EXCEPTIONS */ +#endif /* __STL_USE_EXCEPTIONS */ } namespace NPrivate { @@ -1419,13 +1419,13 @@ namespace NPrivate { } [[noreturn]] void ThrowKeyNotFoundInHashTableException(const TStringBuf keyRepresentation); -} +} template <class Key, class T, class HashFcn, class EqualKey, class Alloc> class THashMap: public TMapOps<THashMap<Key, T, HashFcn, EqualKey, Alloc>> { private: using ht = THashTable<std::pair<const Key, T>, Key, HashFcn, TSelect1st, EqualKey, Alloc>; - ht rep; + ht rep; public: using key_type = typename ht::key_type; @@ -1449,64 +1449,64 @@ public: hasher hash_function() const { return rep.hash_function(); - } - key_equal key_eq() const { - return rep.key_eq(); - } + } + key_equal key_eq() const { + return rep.key_eq(); + } public: THashMap() - : rep(0, hasher(), key_equal()) - { - } - template <class TAllocParam> + : rep(0, hasher(), key_equal()) + { + } + template <class TAllocParam> explicit THashMap(TAllocParam* allocParam, size_type n = 0) : rep(n, hasher(), key_equal(), allocParam) - { - } + { + } explicit THashMap(size_type n) - : rep(n, hasher(), key_equal()) - { - } + : rep(n, hasher(), key_equal()) + { + } THashMap(size_type n, const hasher& hf) - : rep(n, hf, key_equal()) - { - } + : rep(n, hf, key_equal()) + { + } THashMap(size_type n, const hasher& hf, const key_equal& eql) - : rep(n, hf, eql) - { - } - template <class TAllocParam> + : rep(n, hf, eql) + { + } + template <class TAllocParam> explicit THashMap(size_type n, TAllocParam* allocParam) - : rep(n, hasher(), key_equal(), allocParam) - { - } - template <class InputIterator> + : rep(n, hasher(), key_equal(), allocParam) + { + } + template <class InputIterator> THashMap(InputIterator f, InputIterator l) - : rep(0, hasher(), key_equal()) - { - rep.insert_unique(f, l); - } - template <class InputIterator> + : rep(0, hasher(), key_equal()) + { + rep.insert_unique(f, l); + } + template <class InputIterator> THashMap(InputIterator f, InputIterator l, size_type n) - : rep(n, hasher(), key_equal()) - { - rep.insert_unique(f, l); - } - template <class InputIterator> + : rep(n, hasher(), key_equal()) + { + rep.insert_unique(f, l); + } + template <class InputIterator> THashMap(InputIterator f, InputIterator l, size_type n, - const hasher& hf) - : rep(n, hf, key_equal()) - { - rep.insert_unique(f, l); - } - template <class InputIterator> + const hasher& hf) + : rep(n, hf, key_equal()) + { + rep.insert_unique(f, l); + } + template <class InputIterator> THashMap(InputIterator f, InputIterator l, size_type n, - const hasher& hf, const key_equal& eql) - : rep(n, hf, eql) - { - rep.insert_unique(f, l); - } + const hasher& hf, const key_equal& eql) + : rep(n, hf, eql) + { + rep.insert_unique(f, l); + } THashMap(const std::initializer_list<std::pair<Key, T>>& list) : rep(list.size(), hasher(), key_equal()) @@ -1518,47 +1518,47 @@ public: // THashMap has implicit copy/move constructors and copy-/move-assignment operators // because its implementation is backed by THashTable. - // See hash_ut.cpp + // See hash_ut.cpp public: size_type size() const noexcept { - return rep.size(); - } + return rep.size(); + } yssize_t ysize() const noexcept { return (yssize_t)rep.size(); - } + } size_type max_size() const noexcept { - return rep.max_size(); - } - - Y_PURE_FUNCTION bool empty() const noexcept { - return rep.empty(); - } - explicit operator bool() const noexcept { - return !empty(); - } + return rep.max_size(); + } + + Y_PURE_FUNCTION bool empty() const noexcept { + return rep.empty(); + } + explicit operator bool() const noexcept { + return !empty(); + } void swap(THashMap& hs) { - rep.swap(hs.rep); - } - - iterator begin() { - return rep.begin(); - } - iterator end() { - return rep.end(); - } - const_iterator begin() const { - return rep.begin(); - } - const_iterator end() const { - return rep.end(); - } - const_iterator cbegin() const { - return rep.begin(); - } - const_iterator cend() const { - return rep.end(); - } + rep.swap(hs.rep); + } + + iterator begin() { + return rep.begin(); + } + iterator end() { + return rep.end(); + } + const_iterator begin() const { + return rep.begin(); + } + const_iterator end() const { + return rep.end(); + } + const_iterator cbegin() const { + return rep.begin(); + } + const_iterator cend() const { + return rep.end(); + } public: template <class InputIterator> @@ -1567,11 +1567,11 @@ public: } std::pair<iterator, bool> insert(const value_type& obj) { - return rep.insert_unique(obj); - } + return rep.insert_unique(obj); + } template <typename... Args> - std::pair<iterator, bool> emplace(Args&&... args) { + std::pair<iterator, bool> emplace(Args&&... args) { return rep.emplace_unique(std::forward<Args>(args)...); } @@ -1584,10 +1584,10 @@ public: return rep.emplace_unique_noresize(std::forward<Args>(args)...); } - template <class TheObj> - iterator insert_direct(const TheObj& obj, const insert_ctx& ins) { - return rep.insert_direct(obj, ins); - } + template <class TheObj> + iterator insert_direct(const TheObj& obj, const insert_ctx& ins) { + return rep.insert_direct(obj, ins); + } template <typename... Args> iterator emplace_direct(const insert_ctx& ins, Args&&... args) { @@ -1600,29 +1600,29 @@ public: iterator it = find(key, ctx); if (it == end()) { it = rep.emplace_direct(ctx, std::piecewise_construct, - std::forward_as_tuple(std::forward<TKey>(key)), - std::forward_as_tuple(std::forward<Args>(args)...)); + std::forward_as_tuple(std::forward<TKey>(key)), + std::forward_as_tuple(std::forward<Args>(args)...)); return {it, true}; } return {it, false}; } - template <class TheKey> - iterator find(const TheKey& key) { - return rep.find(key); - } - - template <class TheKey> - const_iterator find(const TheKey& key) const { - return rep.find(key); - } - - template <class TheKey> - iterator find(const TheKey& key, insert_ctx& ins) { - return rep.find_i(key, ins); - } - - template <class TheKey> + template <class TheKey> + iterator find(const TheKey& key) { + return rep.find(key); + } + + template <class TheKey> + const_iterator find(const TheKey& key) const { + return rep.find(key); + } + + template <class TheKey> + iterator find(const TheKey& key, insert_ctx& ins) { + return rep.find_i(key, ins); + } + + template <class TheKey> bool contains(const TheKey& key) const { return rep.find(key) != rep.end(); } @@ -1635,103 +1635,103 @@ public: return rep.find_i(key, ins) != rep.end(); } - template <class TKey> - T& operator[](const TKey& key) { + template <class TKey> + T& operator[](const TKey& key) { insert_ctx ctx = nullptr; - iterator it = find(key, ctx); - - if (it != end()) { - return it->second; - } - + iterator it = find(key, ctx); + + if (it != end()) { + return it->second; + } + return rep.emplace_direct(ctx, std::piecewise_construct, std::forward_as_tuple(key), std::forward_as_tuple())->second; - } + } - template <class TheKey> - const T& at(const TheKey& key) const { + template <class TheKey> + const T& at(const TheKey& key) const { using namespace ::NPrivate; - const_iterator it = find(key); + const_iterator it = find(key); if (Y_UNLIKELY(it == end())) { ::NPrivate::ThrowKeyNotFoundInHashTableException(MapKeyToString(key)); - } - - return it->second; + } + + return it->second; } - template <class TheKey> - T& at(const TheKey& key) { + template <class TheKey> + T& at(const TheKey& key) { using namespace ::NPrivate; - iterator it = find(key); + iterator it = find(key); if (Y_UNLIKELY(it == end())) { ::NPrivate::ThrowKeyNotFoundInHashTableException(MapKeyToString(key)); - } + } - return it->second; + return it->second; } - template <class TKey> - size_type count(const TKey& key) const { - return rep.count(key); - } + template <class TKey> + size_type count(const TKey& key) const { + return rep.count(key); + } - template <class TKey> + template <class TKey> std::pair<iterator, iterator> equal_range(const TKey& key) { - return rep.equal_range(key); - } + return rep.equal_range(key); + } - template <class TKey> + template <class TKey> std::pair<const_iterator, const_iterator> equal_range(const TKey& key) const { - return rep.equal_range(key); - } - - template <class TKey> - size_type erase(const TKey& key) { - return rep.erase_one(key); - } - - void erase(iterator it) { - rep.erase(it); - } - void erase(iterator f, iterator l) { - rep.erase(f, l); - } - void clear() { - rep.clear(); - } - void clear(size_t downsize_hint) { - rep.clear(downsize_hint); - } - void basic_clear() { - rep.basic_clear(); - } + return rep.equal_range(key); + } + + template <class TKey> + size_type erase(const TKey& key) { + return rep.erase_one(key); + } + + void erase(iterator it) { + rep.erase(it); + } + void erase(iterator f, iterator l) { + rep.erase(f, l); + } + void clear() { + rep.clear(); + } + void clear(size_t downsize_hint) { + rep.clear(downsize_hint); + } + void basic_clear() { + rep.basic_clear(); + } void release_nodes() { rep.release_nodes(); } - - // if (stHash != NULL) bucket_count() must be equal to stHash->bucket_count() - template <class KeySaver> + + // if (stHash != NULL) bucket_count() must be equal to stHash->bucket_count() + template <class KeySaver> int save_for_st(IOutputStream* stream, KeySaver& ks, sthash<int, int, THash<int>, TEqualTo<int>, typename KeySaver::TSizeType>* stHash = nullptr) const { return rep.template save_for_st<KeySaver>(stream, ks, stHash); - } + } public: void reserve(size_type hint) { rep.reserve(hint); - } - size_type bucket_count() const { - return rep.bucket_count(); - } + } + size_type bucket_count() const { + return rep.bucket_count(); + } size_type bucket_size(size_type n) const { return rep.bucket_size(n); - } - node_allocator_type& GetNodeAllocator() { - return rep.GetNodeAllocator(); - } - const node_allocator_type& GetNodeAllocator() const { - return rep.GetNodeAllocator(); - } + } + node_allocator_type& GetNodeAllocator() { + return rep.GetNodeAllocator(); + } + const node_allocator_type& GetNodeAllocator() const { + return rep.GetNodeAllocator(); + } }; template <class Key, class T, class HashFcn, class EqualKey, class Alloc> @@ -1739,7 +1739,7 @@ inline bool operator==(const THashMap<Key, T, HashFcn, EqualKey, Alloc>& hm1, co if (hm1.size() != hm2.size()) { return false; } - for (const auto& it1 : hm1) { + for (const auto& it1 : hm1) { auto it2 = hm2.find(it1.first); if ((it2 == hm2.end()) || !(it1 == *it2)) { return false; @@ -1757,7 +1757,7 @@ template <class Key, class T, class HashFcn, class EqualKey, class Alloc> class THashMultiMap { private: using ht = THashTable<std::pair<const Key, T>, Key, HashFcn, TSelect1st, EqualKey, Alloc>; - ht rep; + ht rep; public: using key_type = typename ht::key_type; @@ -1780,58 +1780,58 @@ public: hasher hash_function() const { return rep.hash_function(); - } - key_equal key_eq() const { - return rep.key_eq(); - } + } + key_equal key_eq() const { + return rep.key_eq(); + } public: THashMultiMap() - : rep(0, hasher(), key_equal()) - { - } - template <typename TAllocParam> + : rep(0, hasher(), key_equal()) + { + } + template <typename TAllocParam> explicit THashMultiMap(TAllocParam* allocParam) - : rep(0, hasher(), key_equal(), allocParam) - { - } + : rep(0, hasher(), key_equal(), allocParam) + { + } explicit THashMultiMap(size_type n) - : rep(n, hasher(), key_equal()) - { - } + : rep(n, hasher(), key_equal()) + { + } THashMultiMap(size_type n, const hasher& hf) - : rep(n, hf, key_equal()) - { - } + : rep(n, hf, key_equal()) + { + } THashMultiMap(size_type n, const hasher& hf, const key_equal& eql) - : rep(n, hf, eql) - { - } + : rep(n, hf, eql) + { + } - template <class InputIterator> + template <class InputIterator> THashMultiMap(InputIterator f, InputIterator l) - : rep(0, hasher(), key_equal()) - { - rep.insert_equal(f, l); - } - template <class InputIterator> + : rep(0, hasher(), key_equal()) + { + rep.insert_equal(f, l); + } + template <class InputIterator> THashMultiMap(InputIterator f, InputIterator l, size_type n) - : rep(n, hasher(), key_equal()) - { - rep.insert_equal(f, l); - } - template <class InputIterator> + : rep(n, hasher(), key_equal()) + { + rep.insert_equal(f, l); + } + template <class InputIterator> THashMultiMap(InputIterator f, InputIterator l, size_type n, const hasher& hf) - : rep(n, hf, key_equal()) - { - rep.insert_equal(f, l); - } - template <class InputIterator> + : rep(n, hf, key_equal()) + { + rep.insert_equal(f, l); + } + template <class InputIterator> THashMultiMap(InputIterator f, InputIterator l, size_type n, const hasher& hf, const key_equal& eql) - : rep(n, hf, eql) - { - rep.insert_equal(f, l); - } + : rep(n, hf, eql) + { + rep.insert_equal(f, l); + } THashMultiMap(std::initializer_list<std::pair<Key, T>> list) : rep(list.size(), hasher(), key_equal()) @@ -1843,47 +1843,47 @@ public: // THashMultiMap has implicit copy/move constructors and copy-/move-assignment operators // because its implementation is backed by THashTable. - // See hash_ut.cpp + // See hash_ut.cpp public: - size_type size() const { - return rep.size(); - } + size_type size() const { + return rep.size(); + } yssize_t ysize() const { return (yssize_t)rep.size(); - } - size_type max_size() const { - return rep.max_size(); - } - - Y_PURE_FUNCTION bool empty() const { - return rep.empty(); - } - explicit operator bool() const noexcept { - return !empty(); - } + } + size_type max_size() const { + return rep.max_size(); + } + + Y_PURE_FUNCTION bool empty() const { + return rep.empty(); + } + explicit operator bool() const noexcept { + return !empty(); + } void swap(THashMultiMap& hs) { - rep.swap(hs.rep); - } - - iterator begin() { - return rep.begin(); - } - iterator end() { - return rep.end(); - } - const_iterator begin() const { - return rep.begin(); - } - const_iterator end() const { - return rep.end(); - } - const_iterator cbegin() const { - return rep.begin(); - } - const_iterator cend() const { - return rep.end(); - } + rep.swap(hs.rep); + } + + iterator begin() { + return rep.begin(); + } + iterator end() { + return rep.end(); + } + const_iterator begin() const { + return rep.begin(); + } + const_iterator end() const { + return rep.end(); + } + const_iterator cbegin() const { + return rep.begin(); + } + const_iterator cend() const { + return rep.end(); + } public: template <class InputIterator> @@ -1891,18 +1891,18 @@ public: rep.insert_equal(f, l); } - iterator insert(const value_type& obj) { - return rep.insert_equal(obj); - } + iterator insert(const value_type& obj) { + return rep.insert_equal(obj); + } template <typename... Args> - iterator emplace(Args&&... args) { + iterator emplace(Args&&... args) { return rep.emplace_equal(std::forward<Args>(args)...); } - iterator insert_noresize(const value_type& obj) { + iterator insert_noresize(const value_type& obj) { return rep.emplace_equal_noresize(obj); - } + } template <typename... Args> iterator emplace_noresize(Args&&... args) { @@ -1919,15 +1919,15 @@ public: return rep.emplace_direct(ins, std::forward<Args>(args)...); } - template <class TKey> + template <class TKey> const_iterator find(const TKey& key) const { - return rep.find(key); - } + return rep.find(key); + } - template <class TKey> + template <class TKey> iterator find(const TKey& key) { - return rep.find(key); - } + return rep.find(key); + } template <class TheKey> iterator find(const TheKey& key, insert_ctx& ins) { @@ -1939,39 +1939,39 @@ public: return rep.find(key) != rep.end(); } - template <class TKey> - size_type count(const TKey& key) const { - return rep.count(key); - } - - template <class TKey> + template <class TKey> + size_type count(const TKey& key) const { + return rep.count(key); + } + + template <class TKey> std::pair<iterator, iterator> equal_range(const TKey& key) { - return rep.equal_range(key); - } - - template <class TKey> + return rep.equal_range(key); + } + + template <class TKey> std::pair<const_iterator, const_iterator> equal_range(const TKey& key) const { - return rep.equal_range(key); - } - - size_type erase(const key_type& key) { - return rep.erase(key); - } - void erase(iterator it) { - rep.erase(it); - } - void erase(iterator f, iterator l) { - rep.erase(f, l); - } - void clear() { - rep.clear(); - } - void clear(size_t downsize_hint) { - rep.clear(downsize_hint); - } - void basic_clear() { - rep.basic_clear(); - } + return rep.equal_range(key); + } + + size_type erase(const key_type& key) { + return rep.erase(key); + } + void erase(iterator it) { + rep.erase(it); + } + void erase(iterator f, iterator l) { + rep.erase(f, l); + } + void clear() { + rep.clear(); + } + void clear(size_t downsize_hint) { + rep.clear(downsize_hint); + } + void basic_clear() { + rep.basic_clear(); + } void release_nodes() { rep.release_nodes(); } @@ -1985,13 +1985,13 @@ public: public: void reserve(size_type hint) { rep.reserve(hint); - } - size_type bucket_count() const { - return rep.bucket_count(); - } + } + size_type bucket_count() const { + return rep.bucket_count(); + } size_type bucket_size(size_type n) const { return rep.bucket_size(n); - } + } }; template <class Key, class T, class HF, class EqKey, class Alloc> @@ -2008,8 +2008,8 @@ inline bool operator==(const THashMultiMap<Key, T, HF, EqKey, Alloc>& hm1, const TEqualRange eq1 = hm1.equal_range(it->first); TEqualRange eq2 = hm2.equal_range(it->first); if (std::distance(eq1.first, eq1.second) != std::distance(eq2.first, eq2.second) || - !std::is_permutation(eq1.first, eq1.second, eq2.first)) - { + !std::is_permutation(eq1.first, eq1.second, eq2.first)) + { return false; } it = eq1.second; diff --git a/util/generic/hash_primes.cpp b/util/generic/hash_primes.cpp index 6ea00b3918..656d31e046 100644 --- a/util/generic/hash_primes.cpp +++ b/util/generic/hash_primes.cpp @@ -1,21 +1,21 @@ #include "hash_primes.h" #include "array_size.h" -#include "algorithm.h" +#include "algorithm.h" /// Order of fields: reciprocal, reciprocal shift, adjacent hint, divisor #if defined(_32_) static constexpr ::NPrivate::THashDivisor PRIME_DIVISORS_HOLDER[]{ - {0x00000000u, 0u, -1, 0xffffffffu}, // guard value, not a valid divisor - {0x24924925u, 2u, 0, 7u}, - {0xe1e1e1e2u, 4u, 1, 17u}, - {0x1a7b9612u, 4u, 2, 29u}, - {0x3521cfb3u, 5u, 3, 53u}, - {0x51d07eafu, 6u, 4, 97u}, - {0x53909490u, 7u, 5, 193u}, - {0x50f22e12u, 8u, 6, 389u}, - {0x54e3b41au, 9u, 7, 769u}, - {0x53c8eaeeu, 10u, 8, 1543u}, - {0x548eacc6u, 11u, 9, 3079u}, + {0x00000000u, 0u, -1, 0xffffffffu}, // guard value, not a valid divisor + {0x24924925u, 2u, 0, 7u}, + {0xe1e1e1e2u, 4u, 1, 17u}, + {0x1a7b9612u, 4u, 2, 29u}, + {0x3521cfb3u, 5u, 3, 53u}, + {0x51d07eafu, 6u, 4, 97u}, + {0x53909490u, 7u, 5, 193u}, + {0x50f22e12u, 8u, 6, 389u}, + {0x54e3b41au, 9u, 7, 769u}, + {0x53c8eaeeu, 10u, 8, 1543u}, + {0x548eacc6u, 11u, 9, 3079u}, {0x54f1e41eu, 12u, 10, 6151u}, {0x554e390au, 13u, 11, 12289u}, {0x5518ee41u, 14u, 12, 24593u}, @@ -40,17 +40,17 @@ static constexpr ::NPrivate::THashDivisor PRIME_DIVISORS_HOLDER[]{ }; #else static constexpr ::NPrivate::THashDivisor PRIME_DIVISORS_HOLDER[]{ - {0x0000000000000000ul, 0u, -1, 0xffffffffu}, // guard value, not a valid divisor - {0x2492492492492493ul, 2u, 0, 7u}, - {0xe1e1e1e1e1e1e1e2ul, 4u, 1, 17u}, - {0x1a7b9611a7b9611bul, 4u, 2, 29u}, - {0x3521cfb2b78c1353ul, 5u, 3, 53u}, - {0x51d07eae2f8151d1ul, 6u, 4, 97u}, - {0x5390948f40feac70ul, 7u, 5, 193u}, - {0x50f22e111c4c56dful, 8u, 6, 389u}, - {0x54e3b4194ce65de1ul, 9u, 7, 769u}, - {0x53c8eaedea6e7f17ul, 10u, 8, 1543u}, - {0x548eacc5e1e6e3fcul, 11u, 9, 3079u}, + {0x0000000000000000ul, 0u, -1, 0xffffffffu}, // guard value, not a valid divisor + {0x2492492492492493ul, 2u, 0, 7u}, + {0xe1e1e1e1e1e1e1e2ul, 4u, 1, 17u}, + {0x1a7b9611a7b9611bul, 4u, 2, 29u}, + {0x3521cfb2b78c1353ul, 5u, 3, 53u}, + {0x51d07eae2f8151d1ul, 6u, 4, 97u}, + {0x5390948f40feac70ul, 7u, 5, 193u}, + {0x50f22e111c4c56dful, 8u, 6, 389u}, + {0x54e3b4194ce65de1ul, 9u, 7, 769u}, + {0x53c8eaedea6e7f17ul, 10u, 8, 1543u}, + {0x548eacc5e1e6e3fcul, 11u, 9, 3079u}, {0x54f1e41d7767d70cul, 12u, 10, 6151u}, {0x554e39097a781d80ul, 13u, 11, 12289u}, {0x5518ee4079ea6929ul, 14u, 12, 24593u}, @@ -76,9 +76,9 @@ static constexpr ::NPrivate::THashDivisor PRIME_DIVISORS_HOLDER[]{ #endif static constexpr const ::NPrivate::THashDivisor* PRIME_DIVISORS = &PRIME_DIVISORS_HOLDER[1]; ///< Address of the first valid divisor -static constexpr size_t PRIME_DIVISORS_SIZE = Y_ARRAY_SIZE(PRIME_DIVISORS_HOLDER) - 1; ///< Number of valid divisors without the guarding value +static constexpr size_t PRIME_DIVISORS_SIZE = Y_ARRAY_SIZE(PRIME_DIVISORS_HOLDER) - 1; ///< Number of valid divisors without the guarding value -unsigned long HashBucketCount(unsigned long elementCount) { +unsigned long HashBucketCount(unsigned long elementCount) { return HashBucketCountExt(elementCount)(); } @@ -92,10 +92,10 @@ Y_CONST_FUNCTION ::NPrivate::THashDivisor HashBucketCountExt(unsigned long elementCount) { if (elementCount <= PRIME_DIVISORS[0]()) { return PRIME_DIVISORS[0]; - } - + } + return HashBucketBoundedSearch(elementCount); -} +} Y_CONST_FUNCTION ::NPrivate::THashDivisor HashBucketCountExt(unsigned long elementCount, int hint) { diff --git a/util/generic/hash_primes.h b/util/generic/hash_primes.h index 26b6073d4e..4dc2da0b8f 100644 --- a/util/generic/hash_primes.h +++ b/util/generic/hash_primes.h @@ -4,7 +4,7 @@ #include <util/system/types.h> #if defined(_MSC_VER) && defined(_M_X64) - #include <intrin.h> + #include <intrin.h> #endif /** @@ -16,7 +16,7 @@ * greater or equal to `elementCount`. */ Y_CONST_FUNCTION -unsigned long HashBucketCount(unsigned long elementCount); +unsigned long HashBucketCount(unsigned long elementCount); namespace NPrivate { @@ -25,7 +25,7 @@ namespace NPrivate { template <typename TDivisor, typename TDividend, typename MulUnsignedUpper> class TReciprocalDivisor { static_assert(sizeof(TDivisor) <= sizeof(TDividend), "TDivisor and TDividend should have the same size"); - + public: constexpr TReciprocalDivisor() noexcept = default; @@ -80,9 +80,9 @@ namespace NPrivate { #if defined(_32_) using THashDivisor = ::NPrivate::TReciprocalDivisor<ui32, ui32, TMulUnsignedUpper<ui32, ui64, 32>>; #else - #if defined(Y_HAVE_INT128) + #if defined(Y_HAVE_INT128) using THashDivisor = ::NPrivate::TReciprocalDivisor<ui32, ui64, TMulUnsignedUpper<ui64, unsigned __int128, 64>>; - #elif defined(_MSC_VER) && defined(_M_X64) + #elif defined(_MSC_VER) && defined(_M_X64) struct TMulUnsignedUpperVCIntrin { /// Return the high 64 bits of the product of two 64-bit unsigned integers. Y_FORCE_INLINE ui64 operator()(ui64 a, ui64 b) const noexcept { @@ -90,7 +90,7 @@ namespace NPrivate { } }; using THashDivisor = ::NPrivate::TReciprocalDivisor<ui32, ui64, TMulUnsignedUpperVCIntrin>; - #else + #else template <typename TDivisor, typename TDividend> class TNaiveDivisor { public: @@ -127,7 +127,7 @@ namespace NPrivate { }; using THashDivisor = ::NPrivate::TNaiveDivisor<ui32, ui64>; - #endif + #endif #endif } diff --git a/util/generic/hash_primes_ut.cpp b/util/generic/hash_primes_ut.cpp index ff79bae3ba..7b5bf8b5c9 100644 --- a/util/generic/hash_primes_ut.cpp +++ b/util/generic/hash_primes_ut.cpp @@ -1,18 +1,18 @@ -#include "hash_primes.h" - +#include "hash_primes.h" + #include <library/cpp/testing/unittest/registar.h> - + #include <util/generic/vector.h> #include <util/string/builder.h> #include <util/random/fast.h> Y_UNIT_TEST_SUITE(TestHashPrimes) { Y_UNIT_TEST(Test1) { - UNIT_ASSERT_VALUES_EQUAL(HashBucketCount(1), 7); - UNIT_ASSERT_VALUES_EQUAL(HashBucketCount(6), 7); - UNIT_ASSERT_VALUES_EQUAL(HashBucketCount(7), 7); - UNIT_ASSERT_VALUES_EQUAL(HashBucketCount(8), 17); - } + UNIT_ASSERT_VALUES_EQUAL(HashBucketCount(1), 7); + UNIT_ASSERT_VALUES_EQUAL(HashBucketCount(6), 7); + UNIT_ASSERT_VALUES_EQUAL(HashBucketCount(7), 7); + UNIT_ASSERT_VALUES_EQUAL(HashBucketCount(8), 17); + } static TVector<size_t> Numbers() { TVector<size_t> numbers; @@ -77,4 +77,4 @@ Y_UNIT_TEST_SUITE(TestHashPrimes) { } } } -} +} diff --git a/util/generic/hash_set.cpp b/util/generic/hash_set.cpp index a03839b7da..8fabeeabd8 100644 --- a/util/generic/hash_set.cpp +++ b/util/generic/hash_set.cpp @@ -1 +1 @@ -#include "hash_set.h" +#include "hash_set.h" diff --git a/util/generic/hash_set.h b/util/generic/hash_set.h index 68f1880031..e8088cf23b 100644 --- a/util/generic/hash_set.h +++ b/util/generic/hash_set.h @@ -1,8 +1,8 @@ -#pragma once - +#pragma once + #include "fwd.h" #include "hash.h" - + #include <initializer_list> #include <utility> @@ -12,7 +12,7 @@ template <class Value, class HashFcn, class EqualKey, class Alloc> class THashSet { private: using ht = THashTable<Value, Value, HashFcn, ::TIdentity, EqualKey, Alloc>; - ht rep; + ht rep; using mutable_iterator = typename ht::iterator; @@ -37,31 +37,31 @@ public: hasher hash_function() const { return rep.hash_function(); - } - key_equal key_eq() const { - return rep.key_eq(); - } + } + key_equal key_eq() const { + return rep.key_eq(); + } public: THashSet() { - } - template <class TT> + } + template <class TT> explicit THashSet(TT* allocParam, size_type n = 0) : rep(n, hasher(), key_equal(), allocParam) - { - } + { + } explicit THashSet(size_type n) - : rep(n, hasher(), key_equal()) - { - } + : rep(n, hasher(), key_equal()) + { + } THashSet(size_type n, const hasher& hf) - : rep(n, hf, key_equal()) - { - } + : rep(n, hf, key_equal()) + { + } THashSet(size_type n, const hasher& hf, const key_equal& eql) - : rep(n, hf, eql) - { - } + : rep(n, hf, eql) + { + } THashSet(std::initializer_list<value_type> list) : rep(list.size(), hasher(), key_equal()) @@ -84,67 +84,67 @@ public: rep.insert_unique(list.begin(), list.end()); } - template <class InputIterator> + template <class InputIterator> THashSet(InputIterator f, InputIterator l) - : rep(0, hasher(), key_equal()) - { - rep.insert_unique(f, l); - } - template <class InputIterator> + : rep(0, hasher(), key_equal()) + { + rep.insert_unique(f, l); + } + template <class InputIterator> THashSet(InputIterator f, InputIterator l, size_type n) - : rep(n, hasher(), key_equal()) - { - rep.insert_unique(f, l); - } - template <class InputIterator> + : rep(n, hasher(), key_equal()) + { + rep.insert_unique(f, l); + } + template <class InputIterator> THashSet(InputIterator f, InputIterator l, size_type n, - const hasher& hf) - : rep(n, hf, key_equal()) - { - rep.insert_unique(f, l); - } - template <class InputIterator> + const hasher& hf) + : rep(n, hf, key_equal()) + { + rep.insert_unique(f, l); + } + template <class InputIterator> THashSet(InputIterator f, InputIterator l, size_type n, - const hasher& hf, const key_equal& eql) - : rep(n, hf, eql) - { - rep.insert_unique(f, l); - } + const hasher& hf, const key_equal& eql) + : rep(n, hf, eql) + { + rep.insert_unique(f, l); + } // THashSet has implicit copy/move constructors and copy-/move-assignment operators // because its implementation is backed by THashTable. - // See hash_ut.cpp + // See hash_ut.cpp public: - size_type size() const { - return rep.size(); - } - size_type max_size() const { - return rep.max_size(); - } - - Y_PURE_FUNCTION bool empty() const { - return rep.empty(); - } - explicit operator bool() const noexcept { - return !empty(); - } + size_type size() const { + return rep.size(); + } + size_type max_size() const { + return rep.max_size(); + } + + Y_PURE_FUNCTION bool empty() const { + return rep.empty(); + } + explicit operator bool() const noexcept { + return !empty(); + } void swap(THashSet& hs) { - rep.swap(hs.rep); - } - - iterator begin() const { - return rep.begin(); - } - iterator end() const { - return rep.end(); - } - iterator cbegin() const { - return rep.begin(); - } - iterator cend() const { - return rep.end(); - } + rep.swap(hs.rep); + } + + iterator begin() const { + return rep.begin(); + } + iterator end() const { + return rep.end(); + } + iterator cbegin() const { + return rep.begin(); + } + iterator cend() const { + return rep.end(); + } public: void insert(std::initializer_list<value_type> ilist) { @@ -160,7 +160,7 @@ public: std::pair<mutable_iterator, bool> p = rep.insert_unique(obj); return std::pair<iterator, bool>(p.first, p.second); } - template <typename... Args> + template <typename... Args> std::pair<iterator, bool> emplace(Args&&... args) { std::pair<mutable_iterator, bool> p = rep.emplace_unique(std::forward<Args>(args)...); return std::pair<iterator, bool>(p.first, p.second); @@ -174,32 +174,32 @@ public: std::pair<iterator, bool> insert_noresize(const value_type& obj) { std::pair<mutable_iterator, bool> p = rep.insert_unique_noresize(obj); return std::pair<iterator, bool>(p.first, p.second); - } - template <typename... Args> + } + template <typename... Args> std::pair<iterator, bool> emplace_noresize(Args&&... args) { std::pair<mutable_iterator, bool> p = rep.emplace_unique_noresize(std::forward<Args>(args)...); return std::pair<iterator, bool>(p.first, p.second); } - template <class TheObj> - iterator insert_direct(const TheObj& obj, const insert_ctx& ins) { - return rep.insert_direct(obj, ins); - } + template <class TheObj> + iterator insert_direct(const TheObj& obj, const insert_ctx& ins) { + return rep.insert_direct(obj, ins); + } template <typename... Args> iterator emplace_direct(const insert_ctx& ins, Args&&... args) { return rep.emplace_direct(ins, std::forward<Args>(args)...); } - template <class TheKey> + template <class TheKey> const_iterator find(const TheKey& key) const { - return rep.find(key); - } - template <class TheKey> - iterator find(const TheKey& key, insert_ctx& ins) { - return rep.find_i(key, ins); - } - - template <class TheKey> + return rep.find(key); + } + template <class TheKey> + iterator find(const TheKey& key, insert_ctx& ins) { + return rep.find_i(key, ins); + } + + template <class TheKey> bool contains(const TheKey& key) const { return rep.find(key) != rep.end(); } @@ -208,56 +208,56 @@ public: return rep.find_i(key, ins) != rep.end(); } - template <class TKey> - size_type count(const TKey& key) const { - return rep.count(key); - } + template <class TKey> + size_type count(const TKey& key) const { + return rep.count(key); + } - template <class TKey> + template <class TKey> std::pair<iterator, iterator> equal_range(const TKey& key) const { - return rep.equal_range(key); - } - - size_type erase(const key_type& key) { - return rep.erase(key); - } - void erase(iterator it) { - rep.erase(it); - } - void erase(iterator f, iterator l) { - rep.erase(f, l); - } - void clear() { - rep.clear(); - } - void clear(size_t downsize_hint) { - rep.clear(downsize_hint); - } - void basic_clear() { - rep.basic_clear(); - } + return rep.equal_range(key); + } + + size_type erase(const key_type& key) { + return rep.erase(key); + } + void erase(iterator it) { + rep.erase(it); + } + void erase(iterator f, iterator l) { + rep.erase(f, l); + } + void clear() { + rep.clear(); + } + void clear(size_t downsize_hint) { + rep.clear(downsize_hint); + } + void basic_clear() { + rep.basic_clear(); + } void release_nodes() { rep.release_nodes(); } - template <class KeySaver> + template <class KeySaver> int save_for_st(IOutputStream* stream, KeySaver& ks) const { return rep.template save_for_st<KeySaver>(stream, ks); - } + } public: void reserve(size_type hint) { rep.reserve(hint); - } - size_type bucket_count() const { - return rep.bucket_count(); - } + } + size_type bucket_count() const { + return rep.bucket_count(); + } size_type bucket_size(size_type n) const { return rep.bucket_size(n); - } - node_allocator_type& GetNodeAllocator() { - return rep.GetNodeAllocator(); - } + } + node_allocator_type& GetNodeAllocator() { + return rep.GetNodeAllocator(); + } }; template <class Value, class HashFcn, class EqualKey, class Alloc> @@ -282,7 +282,7 @@ template <class Value, class HashFcn, class EqualKey, class Alloc> class THashMultiSet { private: using ht = THashTable<Value, Value, HashFcn, ::TIdentity, EqualKey, Alloc>; - ht rep; + ht rep; public: using key_type = typename ht::key_type; @@ -304,55 +304,55 @@ public: hasher hash_function() const { return rep.hash_function(); - } - key_equal key_eq() const { - return rep.key_eq(); - } + } + key_equal key_eq() const { + return rep.key_eq(); + } public: THashMultiSet() - : rep(0, hasher(), key_equal()) - { - } + : rep(0, hasher(), key_equal()) + { + } explicit THashMultiSet(size_type n) - : rep(n, hasher(), key_equal()) - { - } + : rep(n, hasher(), key_equal()) + { + } THashMultiSet(size_type n, const hasher& hf) - : rep(n, hf, key_equal()) - { - } + : rep(n, hf, key_equal()) + { + } THashMultiSet(size_type n, const hasher& hf, const key_equal& eql) - : rep(n, hf, eql) - { - } + : rep(n, hf, eql) + { + } - template <class InputIterator> + template <class InputIterator> THashMultiSet(InputIterator f, InputIterator l) - : rep(0, hasher(), key_equal()) - { - rep.insert_equal(f, l); - } - template <class InputIterator> + : rep(0, hasher(), key_equal()) + { + rep.insert_equal(f, l); + } + template <class InputIterator> THashMultiSet(InputIterator f, InputIterator l, size_type n) - : rep(n, hasher(), key_equal()) - { - rep.insert_equal(f, l); - } - template <class InputIterator> + : rep(n, hasher(), key_equal()) + { + rep.insert_equal(f, l); + } + template <class InputIterator> THashMultiSet(InputIterator f, InputIterator l, size_type n, - const hasher& hf) - : rep(n, hf, key_equal()) - { - rep.insert_equal(f, l); - } - template <class InputIterator> + const hasher& hf) + : rep(n, hf, key_equal()) + { + rep.insert_equal(f, l); + } + template <class InputIterator> THashMultiSet(InputIterator f, InputIterator l, size_type n, - const hasher& hf, const key_equal& eql) - : rep(n, hf, eql) - { - rep.insert_equal(f, l); - } + const hasher& hf, const key_equal& eql) + : rep(n, hf, eql) + { + rep.insert_equal(f, l); + } THashMultiSet(std::initializer_list<value_type> list) : rep(list.size(), hasher(), key_equal()) @@ -362,88 +362,88 @@ public: // THashMultiSet has implicit copy/move constructors and copy-/move-assignment operators // because its implementation is backed by THashTable. - // See hash_ut.cpp + // See hash_ut.cpp public: - size_type size() const { - return rep.size(); - } - size_type max_size() const { - return rep.max_size(); - } - - Y_PURE_FUNCTION bool empty() const { - return rep.empty(); - } - explicit operator bool() const noexcept { - return !empty(); - } + size_type size() const { + return rep.size(); + } + size_type max_size() const { + return rep.max_size(); + } + + Y_PURE_FUNCTION bool empty() const { + return rep.empty(); + } + explicit operator bool() const noexcept { + return !empty(); + } void swap(THashMultiSet& hs) { - rep.swap(hs.rep); - } - - iterator begin() const { - return rep.begin(); - } - iterator end() const { - return rep.end(); - } - iterator cbegin() const { - return rep.begin(); - } - iterator cend() const { - return rep.end(); - } + rep.swap(hs.rep); + } + + iterator begin() const { + return rep.begin(); + } + iterator end() const { + return rep.end(); + } + iterator cbegin() const { + return rep.begin(); + } + iterator cend() const { + return rep.end(); + } public: - iterator insert(const value_type& obj) { - return rep.insert_equal(obj); - } + iterator insert(const value_type& obj) { + return rep.insert_equal(obj); + } template <typename... Args> iterator emplace(Args&&... args) { return rep.emplace_equal(std::forward<Args>(args)...); } - template <class InputIterator> - void insert(InputIterator f, InputIterator l) { - rep.insert_equal(f, l); - } - iterator insert_noresize(const value_type& obj) { - return rep.insert_equal_noresize(obj); - } - - template <class TKey> - iterator find(const TKey& key) const { - return rep.find(key); - } - - template <class TKey> - size_type count(const TKey& key) const { - return rep.count(key); - } - - template <class TKey> + template <class InputIterator> + void insert(InputIterator f, InputIterator l) { + rep.insert_equal(f, l); + } + iterator insert_noresize(const value_type& obj) { + return rep.insert_equal_noresize(obj); + } + + template <class TKey> + iterator find(const TKey& key) const { + return rep.find(key); + } + + template <class TKey> + size_type count(const TKey& key) const { + return rep.count(key); + } + + template <class TKey> std::pair<iterator, iterator> equal_range(const TKey& key) const { - return rep.equal_range(key); - } - - size_type erase(const key_type& key) { - return rep.erase(key); - } - void erase(iterator it) { - rep.erase(it); - } - void erase(iterator f, iterator l) { - rep.erase(f, l); - } - void clear() { - rep.clear(); - } - void clear(size_t downsize_hint) { - rep.clear(downsize_hint); - } - void basic_clear() { - rep.basic_clear(); - } + return rep.equal_range(key); + } + + size_type erase(const key_type& key) { + return rep.erase(key); + } + void erase(iterator it) { + rep.erase(it); + } + void erase(iterator f, iterator l) { + rep.erase(f, l); + } + void clear() { + rep.clear(); + } + void clear(size_t downsize_hint) { + rep.clear(downsize_hint); + } + void basic_clear() { + rep.basic_clear(); + } void release_nodes() { rep.release_nodes(); } @@ -451,16 +451,16 @@ public: public: void reserve(size_type hint) { rep.reserve(hint); - } - size_type bucket_count() const { - return rep.bucket_count(); - } + } + size_type bucket_count() const { + return rep.bucket_count(); + } size_type bucket_size(size_type n) const { return rep.bucket_size(n); - } - node_allocator_type& GetNodeAllocator() { - return rep.GetNodeAllocator(); - } + } + node_allocator_type& GetNodeAllocator() { + return rep.GetNodeAllocator(); + } }; template <class Val, class HashFcn, class EqualKey, class Alloc> diff --git a/util/generic/hash_ut.cpp b/util/generic/hash_ut.cpp index aa0e11bb20..0551d58770 100644 --- a/util/generic/hash_ut.cpp +++ b/util/generic/hash_ut.cpp @@ -1,41 +1,41 @@ -#include "hash.h" -#include "vector.h" -#include "hash_set.h" - +#include "hash.h" +#include "vector.h" +#include "hash_set.h" + #include <library/cpp/testing/common/probe.h> #include <library/cpp/testing/unittest/registar.h> - + #include <utility> #include <util/str_stl.h> #include <util/digest/multi.h> - -static const char star = 42; - -class THashTest: public TTestBase { - UNIT_TEST_SUITE(THashTest); - UNIT_TEST(TestHMapConstructorsAndAssignments); - UNIT_TEST(TestHMap1); + +static const char star = 42; + +class THashTest: public TTestBase { + UNIT_TEST_SUITE(THashTest); + UNIT_TEST(TestHMapConstructorsAndAssignments); + UNIT_TEST(TestHMap1); UNIT_TEST(TestHMapEqualityOperator); UNIT_TEST(TestHMMapEqualityOperator); - UNIT_TEST(TestHMMapConstructorsAndAssignments); - UNIT_TEST(TestHMMap1); + UNIT_TEST(TestHMMapConstructorsAndAssignments); + UNIT_TEST(TestHMMap1); UNIT_TEST(TestHMMapHas); - UNIT_TEST(TestHSetConstructorsAndAssignments); + UNIT_TEST(TestHSetConstructorsAndAssignments); UNIT_TEST(TestHSetSize); - UNIT_TEST(TestHSet2); + UNIT_TEST(TestHSet2); UNIT_TEST(TestHSetEqualityOperator); - UNIT_TEST(TestHMSetConstructorsAndAssignments); + UNIT_TEST(TestHMSetConstructorsAndAssignments); UNIT_TEST(TestHMSetSize); - UNIT_TEST(TestHMSet1); + UNIT_TEST(TestHMSet1); UNIT_TEST(TestHMSetEqualityOperator); UNIT_TEST(TestHMSetEmplace); - UNIT_TEST(TestInsertErase); - UNIT_TEST(TestResizeOnInsertSmartPtrBug) - UNIT_TEST(TestEmpty); - UNIT_TEST(TestDefaultConstructor); - UNIT_TEST(TestSizeOf); - UNIT_TEST(TestInvariants); - UNIT_TEST(TestAllocation); + UNIT_TEST(TestInsertErase); + UNIT_TEST(TestResizeOnInsertSmartPtrBug) + UNIT_TEST(TestEmpty); + UNIT_TEST(TestDefaultConstructor); + UNIT_TEST(TestSizeOf); + UNIT_TEST(TestInvariants); + UNIT_TEST(TestAllocation); UNIT_TEST(TestInsertCopy); UNIT_TEST(TestEmplace); UNIT_TEST(TestEmplaceNoresize); @@ -59,34 +59,34 @@ class THashTest: public TTestBase { UNIT_TEST(TestHMSetInitializerList); UNIT_TEST(TestHSetInsertInitializerList); UNIT_TEST(TestTupleHash); - UNIT_TEST_SUITE_END(); - + UNIT_TEST_SUITE_END(); + using hmset = THashMultiSet<char, hash<char>, TEqualTo<char>>; - -protected: - void TestHMapConstructorsAndAssignments(); - void TestHMap1(); + +protected: + void TestHMapConstructorsAndAssignments(); + void TestHMap1(); void TestHMapEqualityOperator(); void TestHMMapEqualityOperator(); - void TestHMMapConstructorsAndAssignments(); - void TestHMMap1(); + void TestHMMapConstructorsAndAssignments(); + void TestHMMap1(); void TestHMMapHas(); - void TestHSetConstructorsAndAssignments(); + void TestHSetConstructorsAndAssignments(); void TestHSetSize(); - void TestHSet2(); + void TestHSet2(); void TestHSetEqualityOperator(); - void TestHMSetConstructorsAndAssignments(); + void TestHMSetConstructorsAndAssignments(); void TestHMSetSize(); - void TestHMSet1(); + void TestHMSet1(); void TestHMSetEqualityOperator(); void TestHMSetEmplace(); - void TestInsertErase(); - void TestResizeOnInsertSmartPtrBug(); - void TestEmpty(); - void TestDefaultConstructor(); - void TestSizeOf(); - void TestInvariants(); - void TestAllocation(); + void TestInsertErase(); + void TestResizeOnInsertSmartPtrBug(); + void TestEmpty(); + void TestDefaultConstructor(); + void TestSizeOf(); + void TestInvariants(); + void TestAllocation(); void TestInsertCopy(); void TestEmplace(); void TestEmplaceNoresize(); @@ -110,10 +110,10 @@ protected: void TestHMSetInitializerList(); void TestHSetInsertInitializerList(); void TestTupleHash(); -}; - -UNIT_TEST_SUITE_REGISTRATION(THashTest); - +}; + +UNIT_TEST_SUITE_REGISTRATION(THashTest); + void THashTest::TestHMapConstructorsAndAssignments() { using container = THashMap<TString, int>; @@ -125,7 +125,7 @@ void THashTest::TestHMapConstructorsAndAssignments() { UNIT_ASSERT_VALUES_EQUAL(2, c1.size()); UNIT_ASSERT_VALUES_EQUAL(2, c2.size()); - UNIT_ASSERT_VALUES_EQUAL(1, c1.at("one")); /* Note: fails under MSVC since it does not support implicit generation of move constructors. */ + UNIT_ASSERT_VALUES_EQUAL(1, c1.at("one")); /* Note: fails under MSVC since it does not support implicit generation of move constructors. */ UNIT_ASSERT_VALUES_EQUAL(2, c2.at("two")); container c3(std::move(c1)); @@ -148,11 +148,11 @@ void THashTest::TestHMapConstructorsAndAssignments() { UNIT_ASSERT_VALUES_EQUAL(4, c3.size()); UNIT_ASSERT_VALUES_EQUAL(4, c3.at("four")); - const container c4{ - {"one", 1}, - {"two", 2}, + const container c4{ + {"one", 1}, + {"two", 2}, {"three", 3}, - {"four", 4}, + {"four", 4}, }; UNIT_ASSERT_VALUES_EQUAL(4, c4.size()); @@ -165,43 +165,43 @@ void THashTest::TestHMapConstructorsAndAssignments() { UNIT_ASSERT_VALUES_EQUAL(c1["nonexistent"], 0); } -void THashTest::TestHMap1() { +void THashTest::TestHMap1() { using maptype = THashMap<char, TString, THash<char>, TEqualTo<char>>; - maptype m; - // Store mappings between roman numerals and decimals. - m['l'] = "50"; - m['x'] = "20"; // Deliberate mistake. - m['v'] = "5"; - m['i'] = "1"; - UNIT_ASSERT(!strcmp(m['x'].c_str(), "20")); - m['x'] = "10"; // Correct mistake. - UNIT_ASSERT(!strcmp(m['x'].c_str(), "10")); - + maptype m; + // Store mappings between roman numerals and decimals. + m['l'] = "50"; + m['x'] = "20"; // Deliberate mistake. + m['v'] = "5"; + m['i'] = "1"; + UNIT_ASSERT(!strcmp(m['x'].c_str(), "20")); + m['x'] = "10"; // Correct mistake. + UNIT_ASSERT(!strcmp(m['x'].c_str(), "10")); + UNIT_ASSERT(!m.contains('z')); - UNIT_ASSERT(!strcmp(m['z'].c_str(), "")); + UNIT_ASSERT(!strcmp(m['z'].c_str(), "")); UNIT_ASSERT(m.contains('z')); - - UNIT_ASSERT(m.count('z') == 1); + + UNIT_ASSERT(m.count('z') == 1); auto p = m.insert(std::pair<const char, TString>('c', TString("100"))); - - UNIT_ASSERT(p.second); - + + UNIT_ASSERT(p.second); + p = m.insert(std::pair<const char, TString>('c', TString("100"))); - UNIT_ASSERT(!p.second); - - //Some iterators compare check, really compile time checks - maptype::iterator ite(m.begin()); - maptype::const_iterator cite(m.begin()); - cite = m.begin(); - maptype const& cm = m; - cite = cm.begin(); - - UNIT_ASSERT((maptype::const_iterator)ite == cite); - UNIT_ASSERT(!((maptype::const_iterator)ite != cite)); - UNIT_ASSERT(cite == (maptype::const_iterator)ite); - UNIT_ASSERT(!(cite != (maptype::const_iterator)ite)); -} - + UNIT_ASSERT(!p.second); + + //Some iterators compare check, really compile time checks + maptype::iterator ite(m.begin()); + maptype::const_iterator cite(m.begin()); + cite = m.begin(); + maptype const& cm = m; + cite = cm.begin(); + + UNIT_ASSERT((maptype::const_iterator)ite == cite); + UNIT_ASSERT(!((maptype::const_iterator)ite != cite)); + UNIT_ASSERT(cite == (maptype::const_iterator)ite); + UNIT_ASSERT(!(cite != (maptype::const_iterator)ite)); +} + void THashTest::TestHMapEqualityOperator() { using container = THashMap<TString, int>; @@ -290,62 +290,62 @@ void THashTest::TestHMMapConstructorsAndAssignments() { UNIT_ASSERT_VALUES_EQUAL(4, c3.size()); } -void THashTest::TestHMMap1() { +void THashTest::TestHMMap1() { using mmap = THashMultiMap<char, int, THash<char>, TEqualTo<char>>; - mmap m; - - UNIT_ASSERT(m.count('X') == 0); + mmap m; + + UNIT_ASSERT(m.count('X') == 0); m.insert(std::pair<const char, int>('X', 10)); // Standard way. - UNIT_ASSERT(m.count('X') == 1); - + UNIT_ASSERT(m.count('X') == 1); + m.insert(std::pair<const char, int>('X', 20)); // jbuck: standard way - UNIT_ASSERT(m.count('X') == 2); - + UNIT_ASSERT(m.count('X') == 2); + m.insert(std::pair<const char, int>('Y', 32)); // jbuck: standard way - mmap::iterator i = m.find('X'); // Find first match. - - UNIT_ASSERT((*i).first == 'X'); - UNIT_ASSERT((*i).second == 10); + mmap::iterator i = m.find('X'); // Find first match. + + UNIT_ASSERT((*i).first == 'X'); + UNIT_ASSERT((*i).second == 10); ++i; - UNIT_ASSERT((*i).first == 'X'); - UNIT_ASSERT((*i).second == 20); - - i = m.find('Y'); - UNIT_ASSERT((*i).first == 'Y'); - UNIT_ASSERT((*i).second == 32); - - i = m.find('Z'); - UNIT_ASSERT(i == m.end()); - - size_t count = m.erase('X'); - UNIT_ASSERT(count == 2); - - //Some iterators compare check, really compile time checks - mmap::iterator ite(m.begin()); - mmap::const_iterator cite(m.begin()); - - UNIT_ASSERT((mmap::const_iterator)ite == cite); - UNIT_ASSERT(!((mmap::const_iterator)ite != cite)); - UNIT_ASSERT(cite == (mmap::const_iterator)ite); - UNIT_ASSERT(!(cite != (mmap::const_iterator)ite)); - + UNIT_ASSERT((*i).first == 'X'); + UNIT_ASSERT((*i).second == 20); + + i = m.find('Y'); + UNIT_ASSERT((*i).first == 'Y'); + UNIT_ASSERT((*i).second == 32); + + i = m.find('Z'); + UNIT_ASSERT(i == m.end()); + + size_t count = m.erase('X'); + UNIT_ASSERT(count == 2); + + //Some iterators compare check, really compile time checks + mmap::iterator ite(m.begin()); + mmap::const_iterator cite(m.begin()); + + UNIT_ASSERT((mmap::const_iterator)ite == cite); + UNIT_ASSERT(!((mmap::const_iterator)ite != cite)); + UNIT_ASSERT(cite == (mmap::const_iterator)ite); + UNIT_ASSERT(!(cite != (mmap::const_iterator)ite)); + using HMapType = THashMultiMap<size_t, size_t>; - HMapType hmap; - - //We fill the map to implicitely start a rehash. - for (size_t counter = 0; counter < 3077; ++counter) { - hmap.insert(HMapType::value_type(1, counter)); - } - - hmap.insert(HMapType::value_type(12325, 1)); - hmap.insert(HMapType::value_type(12325, 2)); - - UNIT_ASSERT(hmap.count(12325) == 2); - - //At this point 23 goes to the same bucket as 12325, it used to reveal a bug. - hmap.insert(HMapType::value_type(23, 0)); - - UNIT_ASSERT(hmap.count(12325) == 2); + HMapType hmap; + + //We fill the map to implicitely start a rehash. + for (size_t counter = 0; counter < 3077; ++counter) { + hmap.insert(HMapType::value_type(1, counter)); + } + + hmap.insert(HMapType::value_type(12325, 1)); + hmap.insert(HMapType::value_type(12325, 2)); + + UNIT_ASSERT(hmap.count(12325) == 2); + + //At this point 23 goes to the same bucket as 12325, it used to reveal a bug. + hmap.insert(HMapType::value_type(23, 0)); + + UNIT_ASSERT(hmap.count(12325) == 2); UNIT_ASSERT(hmap.bucket_count() > 3000); for (size_t n = 0; n < 10; n++) { @@ -353,8 +353,8 @@ void THashTest::TestHMMap1() { hmap.insert(HMapType::value_type(1, 2)); } UNIT_ASSERT(hmap.bucket_count() < 30); -} - +} + void THashTest::TestHMMapHas() { using mmap = THashMultiMap<char, int, THash<char>, TEqualTo<char>>; mmap m; @@ -506,22 +506,22 @@ void THashTest::TestHMSetSize() { UNIT_ASSERT_VALUES_EQUAL(3, c.size()); } -void THashTest::TestHMSet1() { - hmset s; - UNIT_ASSERT(s.count(star) == 0); - s.insert(star); - UNIT_ASSERT(s.count(star) == 1); - s.insert(star); - UNIT_ASSERT(s.count(star) == 2); +void THashTest::TestHMSet1() { + hmset s; + UNIT_ASSERT(s.count(star) == 0); + s.insert(star); + UNIT_ASSERT(s.count(star) == 1); + s.insert(star); + UNIT_ASSERT(s.count(star) == 2); auto i = s.find(char(40)); - UNIT_ASSERT(i == s.end()); - - i = s.find(star); - UNIT_ASSERT(i != s.end()); - UNIT_ASSERT(*i == '*'); - UNIT_ASSERT(s.erase(star) == 2); -} - + UNIT_ASSERT(i == s.end()); + + i = s.find(star); + UNIT_ASSERT(i != s.end()); + UNIT_ASSERT(*i == '*'); + UNIT_ASSERT(s.erase(star) == 2); +} + void THashTest::TestHMSetEqualityOperator() { using container = THashMultiSet<int>; @@ -560,8 +560,8 @@ void THashTest::TestHMSetEmplace() { TKey(NTesting::TProbeState* state, int key) : TProbe(state) , Key_(key) - { - } + { + } operator size_t() const { return THash<int>()(Key_); @@ -604,45 +604,45 @@ void THashTest::TestHMSetEmplace() { UNIT_ASSERT_EQUAL(state.Destructors, 6); } -void THashTest::TestInsertErase() { +void THashTest::TestInsertErase() { using hmap = THashMap<TString, size_t, THash<TString>, TEqualTo<TString>>; using val_type = hmap::value_type; - - { - hmap values; - - UNIT_ASSERT(values.insert(val_type("foo", 0)).second); - UNIT_ASSERT(values.insert(val_type("bar", 0)).second); - UNIT_ASSERT(values.insert(val_type("abc", 0)).second); - - UNIT_ASSERT(values.erase("foo") == 1); - UNIT_ASSERT(values.erase("bar") == 1); - UNIT_ASSERT(values.erase("abc") == 1); - } - - { - hmap values; - - UNIT_ASSERT(values.insert(val_type("foo", 0)).second); - UNIT_ASSERT(values.insert(val_type("bar", 0)).second); - UNIT_ASSERT(values.insert(val_type("abc", 0)).second); - - UNIT_ASSERT(values.erase("abc") == 1); - UNIT_ASSERT(values.erase("bar") == 1); - UNIT_ASSERT(values.erase("foo") == 1); - } -} + + { + hmap values; + + UNIT_ASSERT(values.insert(val_type("foo", 0)).second); + UNIT_ASSERT(values.insert(val_type("bar", 0)).second); + UNIT_ASSERT(values.insert(val_type("abc", 0)).second); + + UNIT_ASSERT(values.erase("foo") == 1); + UNIT_ASSERT(values.erase("bar") == 1); + UNIT_ASSERT(values.erase("abc") == 1); + } + + { + hmap values; + + UNIT_ASSERT(values.insert(val_type("foo", 0)).second); + UNIT_ASSERT(values.insert(val_type("bar", 0)).second); + UNIT_ASSERT(values.insert(val_type("abc", 0)).second); + + UNIT_ASSERT(values.erase("abc") == 1); + UNIT_ASSERT(values.erase("bar") == 1); + UNIT_ASSERT(values.erase("foo") == 1); + } +} namespace { - struct TItem: public TSimpleRefCount<TItem> { + struct TItem: public TSimpleRefCount<TItem> { const TString Key; const TString Value; TItem(const TString& key, const TString& value) : Key(key) , Value(value) - { - } + { + } }; using TItemPtr = TIntrusivePtr<TItem>; @@ -664,8 +664,8 @@ namespace { struct TItemMap: public TItemMapBase { TItemMap() : TItemMapBase(1, THash<TString>(), TEqualTo<TString>()) - { - } + { + } TItem& Add(const TString& key, const TString& value) { insert_ctx ins; @@ -676,7 +676,7 @@ namespace { return **it; } }; -} +} void THashTest::TestResizeOnInsertSmartPtrBug() { TItemMap map; @@ -729,7 +729,7 @@ void THashTest::TestSizeOf() { } void THashTest::TestInvariants() { - std::set<int> reference_set; + std::set<int> reference_set; THashSet<int> set; for (int i = 0; i < 1000; i++) { @@ -739,21 +739,21 @@ void THashTest::TestInvariants() { UNIT_ASSERT_VALUES_EQUAL(set.size(), 1000); int count0 = 0; - for (int i = 0; i < 1000; i++) { + for (int i = 0; i < 1000; i++) { count0 += (set.find(i) != set.end()) ? 1 : 0; - } + } UNIT_ASSERT_VALUES_EQUAL(count0, 1000); int count1 = 0; - for (auto pos = set.begin(); pos != set.end(); pos++) { + for (auto pos = set.begin(); pos != set.end(); pos++) { ++count1; - } + } UNIT_ASSERT_VALUES_EQUAL(count1, 1000); int count2 = 0; - for (const int& value : set) { + for (const int& value : set) { count2 += (reference_set.find(value) != reference_set.end()) ? 1 : 0; - } + } UNIT_ASSERT_VALUES_EQUAL(count2, 1000); } @@ -761,16 +761,16 @@ struct TAllocatorCounters { TAllocatorCounters() : Allocations(0) , Deallocations(0) - { - } + { + } ~TAllocatorCounters() { - std::allocator<char> allocator; + std::allocator<char> allocator; /* Release whatever was (intentionally) leaked. */ - for (const auto& chunk : Chunks) { + for (const auto& chunk : Chunks) { allocator.deallocate(static_cast<char*>(chunk.first), chunk.second); - } + } } size_t Allocations; @@ -778,34 +778,34 @@ struct TAllocatorCounters { TSet<std::pair<void*, size_t>> Chunks; }; -template <class T> -class TCountingAllocator: public std::allocator<T> { - using base_type = std::allocator<T>; - +template <class T> +class TCountingAllocator: public std::allocator<T> { + using base_type = std::allocator<T>; + public: using size_type = typename base_type::size_type; - template <class Other> + template <class Other> struct rebind { using other = TCountingAllocator<Other>; }; TCountingAllocator() : Counters_(nullptr) - { - } + { + } TCountingAllocator(TAllocatorCounters* counters) : Counters_(counters) - { + { Y_ASSERT(counters); } - template <class Other> + template <class Other> TCountingAllocator(const TCountingAllocator<Other>& other) : Counters_(other.Counters) - { - } + { + } T* allocate(size_type n) { auto result = base_type::allocate(n); @@ -852,9 +852,9 @@ void THashTest::TestAllocation() { int_set set3(set0); UNIT_ASSERT_VALUES_EQUAL(counters.Allocations, 2); /* Copying from an empty set with allocated buckets should not trigger allocations. */ - for (int i = 0; i < 1000; i++) { + for (int i = 0; i < 1000; i++) { set0.insert(i); - } + } size_t allocations = counters.Allocations; set0.clear(); UNIT_ASSERT_VALUES_EQUAL(counters.Allocations, allocations); /* clear() should not trigger allocations. */ @@ -863,17 +863,17 @@ void THashTest::TestAllocation() { UNIT_ASSERT_VALUES_EQUAL(counters.Allocations, counters.Deallocations); } -template <int Value> +template <int Value> class TNonCopyableInt { public: - explicit TNonCopyableInt(int) { - } + explicit TNonCopyableInt(int) { + } TNonCopyableInt() = delete; TNonCopyableInt(const TNonCopyableInt&) = delete; TNonCopyableInt(TNonCopyable&&) = delete; - TNonCopyableInt& operator=(const TNonCopyable&) = delete; - TNonCopyableInt& operator=(TNonCopyable&&) = delete; + TNonCopyableInt& operator=(const TNonCopyable&) = delete; + TNonCopyableInt& operator=(TNonCopyable&&) = delete; operator int() const { return Value; @@ -918,11 +918,11 @@ void THashTest::TestTryEmplace() { static unsigned counter = 0u; struct TCountConstruct { - explicit TCountConstruct(int v) - : value(v) - { - ++counter; - } + explicit TCountConstruct(int v) + : value(v) + { + ++counter; + } TCountConstruct(const TCountConstruct&) = delete; int value; }; @@ -947,15 +947,15 @@ void THashTest::TestTryEmplaceCopyKey() { static unsigned counter = 0u; struct TCountCopy { - explicit TCountCopy(int i) - : Value(i) - { - } - TCountCopy(const TCountCopy& other) - : Value(other.Value) - { - ++counter; - } + explicit TCountCopy(int i) + : Value(i) + { + } + TCountCopy(const TCountCopy& other) + : Value(other.Value) + { + ++counter; + } operator int() const { return Value; @@ -1040,27 +1040,27 @@ void THashTest::TestHSetEmplaceDirect() { void THashTest::TestNonCopyable() { struct TValue: public TNonCopyable { int value; - TValue(int _value = 0) - : value(_value) - { - } - operator int() { - return value; - } + TValue(int _value = 0) + : value(_value) + { + } + operator int() { + return value; + } }; THashMap<int, TValue> hash; hash.emplace(std::piecewise_construct, std::forward_as_tuple(1), std::forward_as_tuple(5)); - auto&& value = hash[1]; + auto&& value = hash[1]; UNIT_ASSERT_VALUES_EQUAL(static_cast<int>(value), 5); - auto&& not_inserted = hash[2]; + auto&& not_inserted = hash[2]; UNIT_ASSERT_VALUES_EQUAL(static_cast<int>(not_inserted), 0); } void THashTest::TestValueInitialization() { THashMap<int, int> hash; - int& value = hash[0]; + int& value = hash[0]; /* Implicitly inserted values should be value-initialized. */ UNIT_ASSERT_VALUES_EQUAL(value, 0); @@ -1087,18 +1087,18 @@ void THashTest::TestReleaseNodes() { using TIntSet = THashSet<int, THash<int>, TEqualTo<int>, TCountingAllocator<int>>; TIntSet set(&counters); - for (int i = 0; i < 3; i++) { + for (int i = 0; i < 3; i++) { set.insert(i); - } + } UNIT_ASSERT_VALUES_EQUAL(counters.Allocations, 4); set.release_nodes(); UNIT_ASSERT_VALUES_EQUAL(counters.Allocations, 4); UNIT_ASSERT_VALUES_EQUAL(set.size(), 0); - for (int i = 10; i < 13; i++) { + for (int i = 10; i < 13; i++) { set.insert(i); - } + } UNIT_ASSERT_VALUES_EQUAL(counters.Allocations, 7); UNIT_ASSERT(set.contains(10)); UNIT_ASSERT(!set.contains(0)); @@ -1113,25 +1113,25 @@ void THashTest::TestReleaseNodes() { } void THashTest::TestAt() { -#define TEST_AT_THROWN_EXCEPTION(SRC_TYPE, DST_TYPE, KEY_TYPE, KEY, MESSAGE) \ - { \ - THashMap<SRC_TYPE, DST_TYPE> testMap; \ - try { \ - KEY_TYPE testKey = KEY; \ - testMap.at(testKey); \ - UNIT_ASSERT_C(false, "THashMap::at(\"" << KEY << "\") should throw"); \ - } catch (const yexception& e) { \ +#define TEST_AT_THROWN_EXCEPTION(SRC_TYPE, DST_TYPE, KEY_TYPE, KEY, MESSAGE) \ + { \ + THashMap<SRC_TYPE, DST_TYPE> testMap; \ + try { \ + KEY_TYPE testKey = KEY; \ + testMap.at(testKey); \ + UNIT_ASSERT_C(false, "THashMap::at(\"" << KEY << "\") should throw"); \ + } catch (const yexception& e) { \ UNIT_ASSERT_C(e.AsStrBuf().Contains(MESSAGE), "Incorrect exception description: got \"" << e.what() << "\", expected: \"" << MESSAGE << "\""); \ - } catch (...) { \ - UNIT_ASSERT_C(false, "THashMap::at(\"" << KEY << "\") should throw yexception"); \ - } \ + } catch (...) { \ + UNIT_ASSERT_C(false, "THashMap::at(\"" << KEY << "\") should throw yexception"); \ + } \ } TEST_AT_THROWN_EXCEPTION(TString, TString, TString, "111", "111"); TEST_AT_THROWN_EXCEPTION(TString, TString, const TString, "111", "111"); TEST_AT_THROWN_EXCEPTION(TString, TString, TStringBuf, "111", "111"); TEST_AT_THROWN_EXCEPTION(TString, TString, const TStringBuf, "111", "111"); - TEST_AT_THROWN_EXCEPTION(TStringBuf, TStringBuf, const char*, "111", "111"); + TEST_AT_THROWN_EXCEPTION(TStringBuf, TStringBuf, const char*, "111", "111"); TEST_AT_THROWN_EXCEPTION(int, int, short, 11, "11"); TEST_AT_THROWN_EXCEPTION(int, int, int, -1, "-1"); TEST_AT_THROWN_EXCEPTION(int, int, long, 111, "111"); @@ -1141,7 +1141,7 @@ void THashTest::TestAt() { TEST_AT_THROWN_EXCEPTION(int, int, unsigned long, 131, "131"); TEST_AT_THROWN_EXCEPTION(int, int, unsigned long long, 1000000000000ll, "1000000000000"); - char key[] = {11, 12, 0, 1, 2, 11, 0}; + char key[] = {11, 12, 0, 1, 2, 11, 0}; TEST_AT_THROWN_EXCEPTION(TString, TString, char*, key, "\\x0B\\x0C"); TEST_AT_THROWN_EXCEPTION(TString, TString, TStringBuf, TStringBuf(key, sizeof(key) - 1), "\\x0B\\x0C\\0\\1\\2\\x0B"); @@ -1193,7 +1193,7 @@ namespace { int A; int B; - bool operator==(const TFoo& o) const { + bool operator==(const TFoo& o) const { return A == o.A && B == o.B; } }; @@ -1227,13 +1227,13 @@ void THashTest::TestHSetInsertInitializerList() { { const THashSet<int> x = {1, 2, 3, 4, 5}; THashSet<int> y; - y.insert({ - 1, - 2, - 3, - 4, - 5, - }); + y.insert({ + 1, + 2, + 3, + 4, + 5, + }); UNIT_ASSERT_VALUES_EQUAL(x, y); } { diff --git a/util/generic/intrlist.cpp b/util/generic/intrlist.cpp index 10b7c2d012..18a9250cc8 100644 --- a/util/generic/intrlist.cpp +++ b/util/generic/intrlist.cpp @@ -1 +1 @@ -#include "intrlist.h" +#include "intrlist.h" diff --git a/util/generic/intrlist.h b/util/generic/intrlist.h index e1a5b57b32..b5d3f2051b 100644 --- a/util/generic/intrlist.h +++ b/util/generic/intrlist.h @@ -1,101 +1,101 @@ #pragma once - -#include "utility.h" - -#include <util/system/yassert.h> -#include <iterator> - -struct TIntrusiveListDefaultTag {}; - -/* - * two-way linked list - */ + +#include "utility.h" + +#include <util/system/yassert.h> +#include <iterator> + +struct TIntrusiveListDefaultTag {}; + +/* + * two-way linked list + */ template <class T, class Tag = TIntrusiveListDefaultTag> class TIntrusiveListItem { private: using TListItem = TIntrusiveListItem<T, Tag>; - + public: inline TIntrusiveListItem() noexcept - : Next_(this) - , Prev_(Next_) - { - } - + : Next_(this) + , Prev_(Next_) + { + } + inline ~TIntrusiveListItem() { Unlink(); } - + public: - Y_PURE_FUNCTION inline bool Empty() const noexcept { + Y_PURE_FUNCTION inline bool Empty() const noexcept { return (Prev_ == this) && (Next_ == this); } - + inline void Unlink() noexcept { if (Empty()) { return; - } - + } + Prev_->SetNext(Next_); Next_->SetPrev(Prev_); - + SetEnd(); } - + inline void LinkBefore(TListItem* before) noexcept { Unlink(); LinkBeforeNoUnlink(before); } - + inline void LinkBeforeNoUnlink(TListItem* before) noexcept { TListItem* const after = before->Prev(); - + after->SetNext(this); SetPrev(after); SetNext(before); before->SetPrev(this); } - + inline void LinkBefore(TListItem& before) noexcept { LinkBefore(&before); } - + inline void LinkAfter(TListItem* after) noexcept { Unlink(); LinkBeforeNoUnlink(after->Next()); } - + inline void LinkAfter(TListItem& after) noexcept { LinkAfter(&after); } - + public: inline TListItem* Prev() noexcept { return Prev_; } - + inline const TListItem* Prev() const noexcept { return Prev_; } - + inline TListItem* Next() noexcept { return Next_; } - + inline const TListItem* Next() const noexcept { return Next_; } - + public: inline void SetEnd() noexcept { Prev_ = this; Next_ = Prev_; } - + inline void SetNext(TListItem* item) noexcept { Next_ = item; } - + inline void SetPrev(TListItem* item) noexcept { Prev_ = item; } @@ -104,25 +104,25 @@ public: inline T* Node() noexcept { return static_cast<T*>(this); } - + inline const T* Node() const noexcept { return static_cast<const T*>(this); } - + private: inline TIntrusiveListItem(const TIntrusiveListItem&) = delete; inline TIntrusiveListItem& operator=(const TIntrusiveListItem&) = delete; private: - TListItem* Next_; - TListItem* Prev_; -}; - + TListItem* Next_; + TListItem* Prev_; +}; + template <class T, class Tag> class TIntrusiveList { private: using TListItem = TIntrusiveListItem<T, Tag>; - + template <class TListItem, class TNode> class TIteratorBase { public: @@ -130,7 +130,7 @@ private: using TReference = TNode&; using TPointer = TNode*; - using iterator_category = std::bidirectional_iterator_tag; + using iterator_category = std::bidirectional_iterator_tag; using difference_type = ptrdiff_t; using value_type = TNode; @@ -139,82 +139,82 @@ private: inline TIteratorBase() noexcept : Item_(nullptr) - { - } - + { + } + template <class TListItem_, class TNode_> inline TIteratorBase(const TIteratorBase<TListItem_, TNode_>& right) noexcept : Item_(right.Item()) { } - + inline TIteratorBase(TItem* item) noexcept : Item_(item) { } - + inline TItem* Item() const noexcept { return Item_; } - + inline void Next() noexcept { Item_ = Item_->Next(); } - + inline void Prev() noexcept { Item_ = Item_->Prev(); } - + template <class TListItem_, class TNode_> inline bool operator==(const TIteratorBase<TListItem_, TNode_>& right) const noexcept { return Item() == right.Item(); } - + template <class TListItem_, class TNode_> inline bool operator!=(const TIteratorBase<TListItem_, TNode_>& right) const noexcept { return Item() != right.Item(); } - + inline TIteratorBase& operator++() noexcept { Next(); - + return *this; } - + inline TIteratorBase operator++(int) noexcept { - TIteratorBase ret(*this); - + TIteratorBase ret(*this); + Next(); - + return ret; } - + inline TIteratorBase& operator--() noexcept { Prev(); - + return *this; } - + inline TIteratorBase operator--(int) noexcept { - TIteratorBase ret(*this); - + TIteratorBase ret(*this); + Prev(); - + return ret; } - + inline TReference operator*() const noexcept { return *Item_->Node(); } - + inline TPointer operator->() const noexcept { return Item_->Node(); } - + private: - TItem* Item_; + TItem* Item_; }; - + template <class TIterator> class TReverseIteratorBase { public: @@ -230,13 +230,13 @@ private: using pointer = typename TIterator::pointer; inline TReverseIteratorBase() noexcept = default; - + template <class TIterator_> inline TReverseIteratorBase(const TReverseIteratorBase<TIterator_>& right) noexcept : Current_(right.Base()) { } - + inline explicit TReverseIteratorBase(TIterator item) noexcept : Current_(item) { @@ -248,7 +248,7 @@ private: inline TItem* Item() const noexcept { TIterator ret = Current_; - + return (--ret).Item(); } @@ -272,65 +272,65 @@ private: inline TReverseIteratorBase& operator++() noexcept { Next(); - + return *this; } - + inline TReverseIteratorBase operator++(int) noexcept { - TReverseIteratorBase ret(*this); - + TReverseIteratorBase ret(*this); + Next(); - + return ret; } - + inline TReverseIteratorBase& operator--() noexcept { Prev(); - + return *this; } - + inline TReverseIteratorBase operator--(int) noexcept { - TReverseIteratorBase ret(*this); - + TReverseIteratorBase ret(*this); + Prev(); - + return ret; } - + inline TReference operator*() const noexcept { TIterator ret = Current_; - + return *--ret; } inline TPointer operator->() const noexcept { TIterator ret = Current_; - + return &*--ret; } private: TIterator Current_; }; - + public: using TIterator = TIteratorBase<TListItem, T>; using TConstIterator = TIteratorBase<const TListItem, const T>; - + using TReverseIterator = TReverseIteratorBase<TIterator>; using TConstReverseIterator = TReverseIteratorBase<TConstIterator>; - + using iterator = TIterator; using const_iterator = TConstIterator; - + using reverse_iterator = TReverseIterator; using const_reverse_iterator = TConstReverseIterator; public: inline void Swap(TIntrusiveList& right) noexcept { TIntrusiveList temp; - + temp.Append(right); Y_ASSERT(right.Empty()); right.Append(*this); @@ -338,7 +338,7 @@ public: this->Append(temp); Y_ASSERT(temp.Empty()); } - + public: inline TIntrusiveList() noexcept = default; @@ -354,17 +354,17 @@ public: } inline explicit operator bool() const noexcept { - return !Empty(); - } - - Y_PURE_FUNCTION inline bool Empty() const noexcept { + return !Empty(); + } + + Y_PURE_FUNCTION inline bool Empty() const noexcept { return End_.Empty(); } - + inline size_t Size() const noexcept { return std::distance(Begin(), End()); } - + inline void Remove(TListItem* item) noexcept { item->Unlink(); } @@ -372,40 +372,40 @@ public: inline void Clear() noexcept { End_.Unlink(); } - + public: inline TIterator Begin() noexcept { return ++End(); } - + inline TIterator End() noexcept { - return TIterator(&End_); + return TIterator(&End_); } - + inline TConstIterator Begin() const noexcept { return ++End(); } - + inline TConstIterator End() const noexcept { - return TConstIterator(&End_); + return TConstIterator(&End_); } - + inline TReverseIterator RBegin() noexcept { - return TReverseIterator(End()); + return TReverseIterator(End()); } - + inline TReverseIterator REnd() noexcept { - return TReverseIterator(Begin()); + return TReverseIterator(Begin()); } - + inline TConstReverseIterator RBegin() const noexcept { - return TConstReverseIterator(End()); + return TConstReverseIterator(End()); } - + inline TConstReverseIterator REnd() const noexcept { - return TConstReverseIterator(Begin()); + return TConstReverseIterator(Begin()); } - + inline TConstIterator CBegin() const noexcept { return Begin(); } @@ -483,27 +483,27 @@ public: inline void PushBack(TListItem* item) noexcept { item->LinkBefore(End_); } - + inline void PushFront(TListItem* item) noexcept { item->LinkAfter(End_); } - + inline T* PopBack() noexcept { TListItem* const ret = End_.Prev(); - + ret->Unlink(); - + return ret->Node(); } - + inline T* PopFront() noexcept { TListItem* const ret = End_.Next(); - + ret->Unlink(); - + return ret->Node(); } - + inline void Append(TIntrusiveList& list) noexcept { Cut(list.Begin(), list.End(), End()); } @@ -511,79 +511,79 @@ public: inline static void Cut(TIterator begin, TIterator end, TIterator pasteBefore) noexcept { if (begin == end) { return; - } - + } + TListItem* const cutFront = begin.Item(); TListItem* const gapBack = end.Item(); - + TListItem* const gapFront = cutFront->Prev(); TListItem* const cutBack = gapBack->Prev(); - + gapFront->SetNext(gapBack); gapBack->SetPrev(gapFront); TListItem* const pasteBack = pasteBefore.Item(); TListItem* const pasteFront = pasteBack->Prev(); - + pasteFront->SetNext(cutFront); cutFront->SetPrev(pasteFront); - + cutBack->SetNext(pasteBack); pasteBack->SetPrev(cutBack); } - + public: template <class TFunctor> - inline void ForEach(TFunctor&& functor) { + inline void ForEach(TFunctor&& functor) { TIterator i = Begin(); - + while (i != End()) { functor(&*(i++)); } } template <class TFunctor> - inline void ForEach(TFunctor&& functor) const { + inline void ForEach(TFunctor&& functor) const { TConstIterator i = Begin(); while (i != End()) { functor(&*(i++)); - } + } } - + template <class TComparer> - inline void QuickSort(TComparer&& comparer) { + inline void QuickSort(TComparer&& comparer) { if (Begin() == End() || ++Begin() == End()) { return; } - + T* const pivot = PopFront(); TIntrusiveList bigger; TIterator i = Begin(); - + while (i != End()) { if (comparer(*pivot, *i)) { bigger.PushBack(&*i++); } else { ++i; - } + } } - + this->QuickSort(comparer); bigger.QuickSort(comparer); - + PushBack(pivot); Append(bigger); } - + private: inline TIntrusiveList(const TIntrusiveList&) = delete; inline TIntrusiveList& operator=(const TIntrusiveList&) = delete; private: TListItem End_; -}; - +}; + template <class T, class D, class Tag> class TIntrusiveListWithAutoDelete: public TIntrusiveList<T, Tag> { public: @@ -592,7 +592,7 @@ public: using TReverseIterator = typename TIntrusiveList<T, Tag>::TReverseIterator; using TConstReverseIterator = typename TIntrusiveList<T, Tag>::TConstReverseIterator; - + using iterator = TIterator; using const_iterator = TConstIterator; @@ -631,62 +631,62 @@ public: inline static void Cut(TIterator begin, TIterator end, TIterator pasteBefore) noexcept { TIntrusiveList<T, Tag>::Cut(begin, end, pasteBefore); } -}; - -/* - * one-way linked list - */ +}; + +/* + * one-way linked list + */ template <class T, class Tag = TIntrusiveListDefaultTag> -class TIntrusiveSListItem { +class TIntrusiveSListItem { private: using TListItem = TIntrusiveSListItem<T, Tag>; - + public: inline TIntrusiveSListItem() noexcept : Next_(nullptr) - { + { } - + inline ~TIntrusiveSListItem() = default; - + inline bool IsEnd() const noexcept { return Next_ == nullptr; - } - + } + inline TListItem* Next() noexcept { return Next_; } - + inline const TListItem* Next() const noexcept { return Next_; } - + inline void SetNext(TListItem* item) noexcept { Next_ = item; } - + public: inline T* Node() noexcept { return static_cast<T*>(this); } - + inline const T* Node() const noexcept { return static_cast<const T*>(this); } - + private: - TListItem* Next_; -}; - + TListItem* Next_; +}; + template <class T, class Tag> -class TIntrusiveSList { +class TIntrusiveSList { private: using TListItem = TIntrusiveSListItem<T, Tag>; - + public: template <class TListItem, class TNode> class TIteratorBase { - public: + public: using TItem = TListItem; using TReference = TNode&; using TPointer = TNode*; @@ -701,94 +701,94 @@ public: : Item_(item) { } - + inline void Next() noexcept { Item_ = Item_->Next(); } - + inline bool operator==(const TIteratorBase& right) const noexcept { return Item_ == right.Item_; } - + inline bool operator!=(const TIteratorBase& right) const noexcept { return Item_ != right.Item_; } - + inline TIteratorBase& operator++() noexcept { Next(); - + return *this; } - + inline TIteratorBase operator++(int) noexcept { TIteratorBase ret(*this); - + Next(); - + return ret; } - + inline TNode& operator*() noexcept { return *Item_->Node(); } - + inline TNode* operator->() noexcept { return Item_->Node(); } - + private: - TListItem* Item_; + TListItem* Item_; }; - + public: using TIterator = TIteratorBase<TListItem, T>; using TConstIterator = TIteratorBase<const TListItem, const T>; - + using iterator = TIterator; using const_iterator = TConstIterator; - + public: inline TIntrusiveSList() noexcept : Begin_(nullptr) - { + { } - + inline void Swap(TIntrusiveSList& right) noexcept { - DoSwap(Begin_, right.Begin_); + DoSwap(Begin_, right.Begin_); } - + inline explicit operator bool() const noexcept { - return !Empty(); - } - - Y_PURE_FUNCTION inline bool Empty() const noexcept { + return !Empty(); + } + + Y_PURE_FUNCTION inline bool Empty() const noexcept { return Begin_ == nullptr; } - + inline size_t Size() const noexcept { return std::distance(Begin(), End()); } - + inline void Clear() noexcept { Begin_ = nullptr; } - + inline TIterator Begin() noexcept { - return TIterator(Begin_); + return TIterator(Begin_); } - + inline TIterator End() noexcept { return TIterator(nullptr); } - + inline TConstIterator Begin() const noexcept { - return TConstIterator(Begin_); + return TConstIterator(Begin_); } - + inline TConstIterator End() const noexcept { return TConstIterator(nullptr); } - + inline TConstIterator CBegin() const noexcept { return Begin(); } @@ -797,7 +797,7 @@ public: return End(); } - //compat methods + //compat methods inline iterator begin() noexcept { return Begin(); } @@ -836,13 +836,13 @@ public: item->SetNext(Begin_); Begin_ = item; } - + inline T* PopFront() noexcept { Y_ASSERT(Begin_); - + TListItem* const ret = Begin_; Begin_ = Begin_->Next(); - + return ret->Node(); } @@ -851,22 +851,22 @@ public: while (!Empty()) { temp.PushFront(PopFront()); - } - + } + this->Swap(temp); } - + template <class TFunctor> inline void ForEach(TFunctor&& functor) const noexcept(noexcept(functor(std::declval<TListItem>().Node()))) { TListItem* i = Begin_; - + while (i) { TListItem* const next = i->Next(); functor(i->Node()); i = next; - } + } } - + private: - TListItem* Begin_; -}; + TListItem* Begin_; +}; diff --git a/util/generic/intrlist_ut.cpp b/util/generic/intrlist_ut.cpp index 2b27ff71b6..eff7cdf2ee 100644 --- a/util/generic/intrlist_ut.cpp +++ b/util/generic/intrlist_ut.cpp @@ -1,19 +1,19 @@ -#include "intrlist.h" - +#include "intrlist.h" + #include <library/cpp/testing/unittest/registar.h> - + #include <util/stream/output.h> - -class TListTest: public TTestBase { - UNIT_TEST_SUITE(TListTest); - UNIT_TEST(TestIterate); - UNIT_TEST(TestRIterate); - UNIT_TEST(TestForEach); - UNIT_TEST(TestForEachWithDelete); - UNIT_TEST(TestSize); - UNIT_TEST(TestQuickSort); - UNIT_TEST(TestCut); - UNIT_TEST(TestAppend); + +class TListTest: public TTestBase { + UNIT_TEST_SUITE(TListTest); + UNIT_TEST(TestIterate); + UNIT_TEST(TestRIterate); + UNIT_TEST(TestForEach); + UNIT_TEST(TestForEachWithDelete); + UNIT_TEST(TestSize); + UNIT_TEST(TestQuickSort); + UNIT_TEST(TestCut); + UNIT_TEST(TestAppend); UNIT_TEST(TestMoveCtor); UNIT_TEST(TestMoveOpEq); UNIT_TEST(TestListWithAutoDelete); @@ -21,17 +21,17 @@ class TListTest: public TTestBase { UNIT_TEST(TestListWithAutoDeleteMoveOpEq); UNIT_TEST(TestListWithAutoDeleteClear); UNIT_TEST(TestSecondTag); - UNIT_TEST_SUITE_END(); - -private: - void TestSize(); - void TestIterate(); - void TestRIterate(); - void TestForEach(); - void TestForEachWithDelete(); - void TestQuickSort(); - void TestCut(); - void TestAppend(); + UNIT_TEST_SUITE_END(); + +private: + void TestSize(); + void TestIterate(); + void TestRIterate(); + void TestForEach(); + void TestForEachWithDelete(); + void TestQuickSort(); + void TestCut(); + void TestAppend(); void TestMoveCtor(); void TestMoveOpEq(); void TestListWithAutoDelete(); @@ -39,17 +39,17 @@ private: void TestListWithAutoDeleteMoveOpEq(); void TestListWithAutoDeleteClear(); void TestSecondTag(); -}; - -UNIT_TEST_SUITE_REGISTRATION(TListTest); - -class TInt: public TIntrusiveListItem<TInt> { -public: +}; + +UNIT_TEST_SUITE_REGISTRATION(TListTest); + +class TInt: public TIntrusiveListItem<TInt> { +public: inline TInt(int value) noexcept - : Value_(value) - { - } - + : Value_(value) + { + } + TInt(TInt&& rhs) noexcept : Value_(rhs.Value_) { @@ -63,25 +63,25 @@ public: } inline operator int&() noexcept { - return Value_; - } - + return Value_; + } + inline operator const int&() const noexcept { - return Value_; - } - -private: - int Value_; -}; - -class TMyList: public TIntrusiveList<TInt> { -public: - inline TMyList(int count) { - while (count > 0) { - PushFront(new TInt(count--)); - } - } - + return Value_; + } + +private: + int Value_; +}; + +class TMyList: public TIntrusiveList<TInt> { +public: + inline TMyList(int count) { + while (count > 0) { + PushFront(new TInt(count--)); + } + } + //TMyList(const TMyList& rhs) = default; TMyList(TMyList&& rhs) noexcept = default; @@ -89,117 +89,117 @@ public: TMyList& operator=(TMyList&& rhs) noexcept = default; inline ~TMyList() { - while (!Empty()) { - delete PopBack(); - } - } -}; - + while (!Empty()) { + delete PopBack(); + } + } +}; + struct TIntGreater: private TGreater<int> { inline bool operator()(const TInt& l, const TInt& r) const noexcept { return TGreater<int>::operator()(l, r); - } -}; - -void TListTest::TestQuickSort() { - TMyList l(1000); - size_t c = 0; - + } +}; + +void TListTest::TestQuickSort() { + TMyList l(1000); + size_t c = 0; + l.QuickSort(TIntGreater()); - - UNIT_ASSERT_EQUAL(l.Size(), 1000); - - for (TMyList::TIterator it = l.Begin(); it != l.End(); ++it) { - UNIT_ASSERT_EQUAL(*it, int(1000 - c++)); - } -} - -void TListTest::TestSize() { - TMyList l(1024); - - UNIT_ASSERT_EQUAL(l.Size(), 1024); -} - -void TListTest::TestIterate() { - TMyList l(1000); - size_t c = 0; - - for (TMyList::TIterator it = l.Begin(); it != l.End(); ++it) { - ++c; - - UNIT_ASSERT_EQUAL(*it, (int)c); - } - - UNIT_ASSERT_EQUAL(c, 1000); -} - -void TListTest::TestRIterate() { - TMyList l(1000); - size_t c = 1000; - + + UNIT_ASSERT_EQUAL(l.Size(), 1000); + + for (TMyList::TIterator it = l.Begin(); it != l.End(); ++it) { + UNIT_ASSERT_EQUAL(*it, int(1000 - c++)); + } +} + +void TListTest::TestSize() { + TMyList l(1024); + + UNIT_ASSERT_EQUAL(l.Size(), 1024); +} + +void TListTest::TestIterate() { + TMyList l(1000); + size_t c = 0; + + for (TMyList::TIterator it = l.Begin(); it != l.End(); ++it) { + ++c; + + UNIT_ASSERT_EQUAL(*it, (int)c); + } + + UNIT_ASSERT_EQUAL(c, 1000); +} + +void TListTest::TestRIterate() { + TMyList l(1000); + size_t c = 1000; + UNIT_ASSERT_EQUAL(l.RBegin(), TMyList::TReverseIterator(l.End())); UNIT_ASSERT_EQUAL(l.REnd(), TMyList::TReverseIterator(l.Begin())); - for (TMyList::TReverseIterator it = l.RBegin(); it != l.REnd(); ++it) { - UNIT_ASSERT_EQUAL(*it, (int)c--); - } - - UNIT_ASSERT_EQUAL(c, 0); -} - -class TSum { -public: - inline TSum(size_t& sum) - : Sum_(sum) - { - } - + for (TMyList::TReverseIterator it = l.RBegin(); it != l.REnd(); ++it) { + UNIT_ASSERT_EQUAL(*it, (int)c--); + } + + UNIT_ASSERT_EQUAL(c, 0); +} + +class TSum { +public: + inline TSum(size_t& sum) + : Sum_(sum) + { + } + inline void operator()(const TInt* v) noexcept { - Sum_ += *v; - } - -private: - size_t& Sum_; -}; - -class TSumWithDelete { -public: - inline TSumWithDelete(size_t& sum) - : Sum_(sum) - { - } - + Sum_ += *v; + } + +private: + size_t& Sum_; +}; + +class TSumWithDelete { +public: + inline TSumWithDelete(size_t& sum) + : Sum_(sum) + { + } + inline void operator()(TInt* v) noexcept { - if (*v % 2) { - Sum_ += *v; - } else { - delete v; - } - } - -private: - size_t& Sum_; -}; - -void TListTest::TestForEach() { - TMyList l(1000); - size_t sum = 0; - TSum functor(sum); - - l.ForEach(functor); - - UNIT_ASSERT_EQUAL(sum, 1000 * 1001 / 2); -} - -void TListTest::TestForEachWithDelete() { - TMyList l(1000); - size_t sum = 0; - TSumWithDelete functor(sum); - - l.ForEach(functor); - - UNIT_ASSERT_EQUAL(sum, 500 * 500 /*== n * (x + y * (n - 1) / 2), x == 1, y == 2*/); -} + if (*v % 2) { + Sum_ += *v; + } else { + delete v; + } + } + +private: + size_t& Sum_; +}; + +void TListTest::TestForEach() { + TMyList l(1000); + size_t sum = 0; + TSum functor(sum); + + l.ForEach(functor); + + UNIT_ASSERT_EQUAL(sum, 1000 * 1001 / 2); +} + +void TListTest::TestForEachWithDelete() { + TMyList l(1000); + size_t sum = 0; + TSumWithDelete functor(sum); + + l.ForEach(functor); + + UNIT_ASSERT_EQUAL(sum, 500 * 500 /*== n * (x + y * (n - 1) / 2), x == 1, y == 2*/); +} static void CheckIterationAfterCut(const TMyList& l, const TMyList& l2, size_t N, size_t M) { size_t c = 0; @@ -283,7 +283,7 @@ static void CheckIterationAfterAppend(const TMyList& l, size_t N, size_t M) { for (size_t i = 1; i <= N; ++i, ++it) { UNIT_ASSERT_EQUAL((int)i, *it); } - + for (size_t i = 1; i <= M; ++i, ++it) { UNIT_ASSERT_EQUAL((int)i, *it); } @@ -301,14 +301,14 @@ static void TestAppend(int N, int M) { } void TListTest::TestAppend() { - ::TestAppend(500, 500); - ::TestAppend(0, 0); - ::TestAppend(1, 0); - ::TestAppend(0, 1); - ::TestAppend(1, 1); -} - -template <typename TListType> + ::TestAppend(500, 500); + ::TestAppend(0, 0); + ::TestAppend(1, 0); + ::TestAppend(0, 1); + ::TestAppend(1, 1); +} + +template <typename TListType> static void CheckList(const TListType& lst) { int i = 1; for (typename TListType::TConstIterator it = lst.Begin(); it != lst.End(); ++it, ++i) { @@ -317,25 +317,25 @@ static void CheckList(const TListType& lst) { } void TListTest::TestMoveCtor() { - const int N{42}; - TMyList lst{N}; + const int N{42}; + TMyList lst{N}; UNIT_ASSERT(!lst.Empty()); UNIT_ASSERT_EQUAL(lst.Size(), N); CheckList(lst); - TMyList nextLst{std::move(lst)}; + TMyList nextLst{std::move(lst)}; UNIT_ASSERT(lst.Empty()); CheckList(nextLst); } void TListTest::TestMoveOpEq() { - const int N{42}; - TMyList lst{N}; + const int N{42}; + TMyList lst{N}; UNIT_ASSERT(!lst.Empty()); UNIT_ASSERT_EQUAL(lst.Size(), N); CheckList(lst); - const int M{2}; + const int M{2}; TMyList nextLst(M); UNIT_ASSERT(!nextLst.Empty()); UNIT_ASSERT_EQUAL(nextLst.Size(), M); @@ -350,16 +350,16 @@ void TListTest::TestMoveOpEq() { class TSelfCountingInt: public TIntrusiveListItem<TSelfCountingInt> { public: TSelfCountingInt(int& counter, int value) noexcept - : Counter_(counter) - , Value_(value) - { + : Counter_(counter) + , Value_(value) + { ++Counter_; } TSelfCountingInt(TSelfCountingInt&& rhs) noexcept - : Counter_(rhs.Counter_) - , Value_(rhs.Value_) - { + : Counter_(rhs.Counter_) + , Value_(rhs.Value_) + { rhs.Value_ = 0xDEAD; } @@ -394,7 +394,7 @@ struct TSelfCountingIntDelete { void TListTest::TestListWithAutoDelete() { using TListType = TIntrusiveListWithAutoDelete<TSelfCountingInt, TSelfCountingIntDelete>; - int counter{0}; + int counter{0}; { TListType lst; UNIT_ASSERT(lst.Empty()); @@ -412,7 +412,7 @@ void TListTest::TestListWithAutoDelete() { void TListTest::TestListWithAutoDeleteMoveCtor() { using TListType = TIntrusiveListWithAutoDelete<TSelfCountingInt, TSelfCountingIntDelete>; - int counter{0}; + int counter{0}; { TListType lst; lst.PushFront(new TSelfCountingInt(counter, 2)); @@ -432,7 +432,7 @@ void TListTest::TestListWithAutoDeleteMoveCtor() { void TListTest::TestListWithAutoDeleteMoveOpEq() { using TListType = TIntrusiveListWithAutoDelete<TSelfCountingInt, TSelfCountingIntDelete>; - int counter{0}; + int counter{0}; { TListType lst; lst.PushFront(new TSelfCountingInt(counter, 2)); @@ -476,16 +476,16 @@ void TListTest::TestListWithAutoDeleteClear() { UNIT_ASSERT_EQUAL(counter, 0); } -struct TSecondTag {}; +struct TSecondTag {}; class TDoubleNode - : public TInt, - public TIntrusiveListItem<TDoubleNode, TSecondTag> { + : public TInt, + public TIntrusiveListItem<TDoubleNode, TSecondTag> { public: - TDoubleNode(int value) noexcept - : TInt(value) - { - } + TDoubleNode(int value) noexcept + : TInt(value) + { + } }; void TListTest::TestSecondTag() { diff --git a/util/generic/is_in.cpp b/util/generic/is_in.cpp index 29902be1ad..4edfd1fe10 100644 --- a/util/generic/is_in.cpp +++ b/util/generic/is_in.cpp @@ -1 +1 @@ -#include "is_in.h" +#include "is_in.h" diff --git a/util/generic/is_in.h b/util/generic/is_in.h index 83f8f5645e..4f175ea5eb 100644 --- a/util/generic/is_in.h +++ b/util/generic/is_in.h @@ -1,53 +1,53 @@ #pragma once - + #include "typetraits.h" -#include <algorithm> +#include <algorithm> #include <initializer_list> template <class I, class T> -static inline bool IsIn(I f, I l, const T& v); +static inline bool IsIn(I f, I l, const T& v); template <class C, class T> -static inline bool IsIn(const C& c, const T& e); +static inline bool IsIn(const C& c, const T& e); namespace NIsInHelper { Y_HAS_MEMBER(find, FindMethod); Y_HAS_SUBTYPE(const_iterator, ConstIterator); Y_HAS_SUBTYPE(key_type, KeyType); - template <class T> + template <class T> using TIsAssocCont = TConjunction<THasFindMethod<T>, THasConstIterator<T>, THasKeyType<T>>; - template <class C, class T, bool isAssoc> - struct TIsInTraits { - static bool IsIn(const C& c, const T& e) { + template <class C, class T, bool isAssoc> + struct TIsInTraits { + static bool IsIn(const C& c, const T& e) { using std::begin; using std::end; return ::IsIn(begin(c), end(c), e); - } - }; - - template <class C, class T> - struct TIsInTraits<C, T, true> { - static bool IsIn(const C& c, const T& e) { - return c.find(e) != c.end(); - } - }; -} + } + }; + + template <class C, class T> + struct TIsInTraits<C, T, true> { + static bool IsIn(const C& c, const T& e) { + return c.find(e) != c.end(); + } + }; +} template <class I, class T> -static inline bool IsIn(I f, I l, const T& v) { - return std::find(f, l, v) != l; +static inline bool IsIn(I f, I l, const T& v) { + return std::find(f, l, v) != l; } template <class C, class T> -static inline bool IsIn(const C& c, const T& e) { +static inline bool IsIn(const C& c, const T& e) { using namespace NIsInHelper; return TIsInTraits<C, T, TIsAssocCont<C>::value>::IsIn(c, e); } template <class T, class U> static inline bool IsIn(std::initializer_list<T> l, const U& e) { - return ::IsIn(l.begin(), l.end(), e); + return ::IsIn(l.begin(), l.end(), e); } diff --git a/util/generic/is_in_ut.cpp b/util/generic/is_in_ut.cpp index 77a0a4bd2c..c668bce807 100644 --- a/util/generic/is_in_ut.cpp +++ b/util/generic/is_in_ut.cpp @@ -1,18 +1,18 @@ #include <library/cpp/testing/unittest/registar.h> -#include "algorithm.h" -#include "hash.h" -#include "hash_set.h" -#include "is_in.h" -#include "map.h" -#include "set.h" -#include "strbuf.h" +#include "algorithm.h" +#include "hash.h" +#include "hash_set.h" +#include "is_in.h" +#include "map.h" +#include "set.h" +#include "strbuf.h" #include "string.h" Y_UNIT_TEST_SUITE(TIsIn) { - template <class TCont, class T> + template <class TCont, class T> void TestIsInWithCont(const T& elem) { - class TMapMock: public TCont { + class TMapMock: public TCont { public: typename TCont::const_iterator find(const typename TCont::key_type& k) const { ++FindCalled; @@ -106,7 +106,7 @@ Y_UNIT_TEST_SUITE(TIsIn) { } Y_UNIT_TEST(IsInArrayTest) { - const TString array[] = {"a", "b", "d"}; + const TString array[] = {"a", "b", "d"}; UNIT_ASSERT(IsIn(array, "a")); UNIT_ASSERT(IsIn(array, TString("b"))); diff --git a/util/generic/iterator.cpp b/util/generic/iterator.cpp index 437a096e6b..7c5c206cc3 100644 --- a/util/generic/iterator.cpp +++ b/util/generic/iterator.cpp @@ -1 +1 @@ -#include "iterator.h" +#include "iterator.h" diff --git a/util/generic/iterator.h b/util/generic/iterator.h index 88b4167e7d..19e9d20976 100644 --- a/util/generic/iterator.h +++ b/util/generic/iterator.h @@ -1,35 +1,35 @@ #pragma once - + #include <iterator> #include <utility> -namespace NStlIterator { - template <class T> +namespace NStlIterator { + template <class T> class TProxy { public: TProxy() = default; - TProxy(T&& value) - : Value_(std::move(value)) - { + TProxy(T&& value) + : Value_(std::move(value)) + { } - + const T* operator->() const noexcept { return &Value_; } - + const T& operator*() const noexcept { return Value_; } - + bool operator==(const TProxy& rhs) const { return Value_ == rhs.Value_; - } - + } + private: T Value_; - }; + }; } // namespace NStlIterator - + /** * Range adaptor that turns a derived class with a Java-style iteration * interface into an STL range. @@ -63,11 +63,11 @@ namespace NStlIterator { * } * \endcode */ -template <class TSlave> +template <class TSlave> class TInputRangeAdaptor { public: // TODO: private - class TIterator { - public: + class TIterator { + public: static constexpr bool IsNoexceptNext = noexcept(std::declval<TSlave>().Next()); using difference_type = std::ptrdiff_t; @@ -77,56 +77,56 @@ public: // TODO: private using iterator_category = std::input_iterator_tag; inline TIterator() noexcept - : Slave_(nullptr) - , Cur_() - { - } - + : Slave_(nullptr) + , Cur_() + { + } + inline TIterator(TSlave* slave) noexcept(IsNoexceptNext) - : Slave_(slave) - , Cur_(Slave_->Next()) - { - } - + : Slave_(slave) + , Cur_(Slave_->Next()) + { + } + inline bool operator==(const TIterator& it) const noexcept { - return Cur_ == it.Cur_; - } - + return Cur_ == it.Cur_; + } + inline bool operator!=(const TIterator& it) const noexcept { - return !(*this == it); - } - + return !(*this == it); + } + inline pointer operator->() const noexcept { return Cur_; - } - + } + inline reference operator*() const noexcept { return *Cur_; - } - + } + inline TIterator& operator++() noexcept(IsNoexceptNext) { - Cur_ = Slave_->Next(); - - return *this; - } - - private: - TSlave* Slave_; + Cur_ = Slave_->Next(); + + return *this; + } + + private: + TSlave* Slave_; pointer Cur_; - }; - -public: + }; + +public: using const_iterator = TIterator; using iterator = const_iterator; inline iterator begin() const noexcept(TIterator::IsNoexceptNext) { - return TIterator(const_cast<TSlave*>(static_cast<const TSlave*>(this))); - } - + return TIterator(const_cast<TSlave*>(static_cast<const TSlave*>(this))); + } + inline iterator end() const noexcept { - return TIterator(); - } -}; + return TIterator(); + } +}; /** * Transform given reverse iterator into forward iterator pointing to the same element. diff --git a/util/generic/iterator_range.h b/util/generic/iterator_range.h index 8afbc9d4ae..9f4d02da29 100644 --- a/util/generic/iterator_range.h +++ b/util/generic/iterator_range.h @@ -52,14 +52,14 @@ public: TIteratorRange() : Begin_() , End_() - { - } + { + } TIteratorRange(TIterator begin, TIterator end) : Begin_(begin) , End_(end) - { - } + { + } TIterator begin() const { return Begin_; @@ -69,7 +69,7 @@ public: return End_; } - Y_PURE_FUNCTION bool empty() const { + Y_PURE_FUNCTION bool empty() const { return Begin_ == End_; } diff --git a/util/generic/iterator_ut.cpp b/util/generic/iterator_ut.cpp index e35a6a6651..00be19e10e 100644 --- a/util/generic/iterator_ut.cpp +++ b/util/generic/iterator_ut.cpp @@ -11,7 +11,7 @@ Y_UNIT_TEST_SUITE(TIterator) { } Y_UNIT_TEST_SUITE(TInputRangeAdaptor) { - class TSquaresGenerator: public TInputRangeAdaptor<TSquaresGenerator> { + class TSquaresGenerator: public TInputRangeAdaptor<TSquaresGenerator> { public: const i64* Next() { Current_ = State_ * State_; @@ -36,11 +36,11 @@ Y_UNIT_TEST_SUITE(TInputRangeAdaptor) { } } - class TUrlPart: public TInputRangeAdaptor<TUrlPart> { + class TUrlPart: public TInputRangeAdaptor<TUrlPart> { public: - TUrlPart(const TStringBuf& url) - : Url_(url) - { + TUrlPart(const TStringBuf& url) + : Url_(url) + { } NStlIterator::TProxy<TStringBuf> Next() { @@ -55,8 +55,8 @@ Y_UNIT_TEST_SUITE(TInputRangeAdaptor) { const TVector<TStringBuf> expected = {TStringBuf("yandex.ru"), TStringBuf("search?")}; auto expected_part = expected.begin(); for (const TStringBuf& part : TUrlPart(TStringBuf("yandex.ru/search?"))) { - UNIT_ASSERT_VALUES_EQUAL(part, *expected_part); - ++expected_part; + UNIT_ASSERT_VALUES_EQUAL(part, *expected_part); + ++expected_part; } UNIT_ASSERT(expected_part == expected.end()); } diff --git a/util/generic/lazy_value.h b/util/generic/lazy_value.h index 00751806e2..3c720f76b5 100644 --- a/util/generic/lazy_value.h +++ b/util/generic/lazy_value.h @@ -1,7 +1,7 @@ #pragma once #include "maybe.h" -#include "function.h" +#include "function.h" template <class T> class TLazyValueBase { @@ -51,16 +51,16 @@ private: // we need this to get implicit construction TLazyValue from lambda // and save default copy constructor and operator= for type TLazyValue template <class T> -class TLazyValue: public TLazyValueBase<T> { +class TLazyValue: public TLazyValueBase<T> { public: template <typename... TArgs> TLazyValue(TArgs&&... args) : TLazyValueBase<T>(std::forward<TArgs>(args)...) - { - } + { + } }; -template <typename F> -TLazyValue<TFunctionResult<F>> MakeLazy(F&& f) { - return {std::forward<F>(f)}; +template <typename F> +TLazyValue<TFunctionResult<F>> MakeLazy(F&& f) { + return {std::forward<F>(f)}; } diff --git a/util/generic/lazy_value_ut.cpp b/util/generic/lazy_value_ut.cpp index 07aa44538e..f6135880c3 100644 --- a/util/generic/lazy_value_ut.cpp +++ b/util/generic/lazy_value_ut.cpp @@ -4,7 +4,7 @@ Y_UNIT_TEST_SUITE(TLazyValueTestSuite) { Y_UNIT_TEST(TestLazyValue) { - TLazyValue<int> value([]() { + TLazyValue<int> value([]() { return 5; }); UNIT_ASSERT(!value); @@ -13,9 +13,9 @@ Y_UNIT_TEST_SUITE(TLazyValueTestSuite) { } Y_UNIT_TEST(TestLazyValueInitialization) { - TLazyValue<int> value1([]() { return 5; }); + TLazyValue<int> value1([]() { return 5; }); - TLazyValue<int> value2 = []() { return 5; }; + TLazyValue<int> value2 = []() { return 5; }; TLazyValue<int> notInitialized{}; @@ -25,7 +25,7 @@ Y_UNIT_TEST_SUITE(TLazyValueTestSuite) { } Y_UNIT_TEST(TestLazyValueCopy) { - TLazyValue<int> value([]() { return 5; }); + TLazyValue<int> value([]() { return 5; }); UNIT_ASSERT(!value); TLazyValue<int> emptyCopy = value; @@ -75,7 +75,7 @@ Y_UNIT_TEST_SUITE(TLazyValueTestSuite) { Y_UNIT_TEST(TestLazyValueMoveValueInitialization) { size_t numCopies = 0; TCopyCounter counter{numCopies}; - TLazyValue<TCopyCounter> value{[v = std::move(counter)]() mutable { return std::move(v); }}; + TLazyValue<TCopyCounter> value{[v = std::move(counter)]() mutable { return std::move(v); }}; value.InitDefault(); UNIT_ASSERT_EQUAL(numCopies, 0); } @@ -83,7 +83,7 @@ Y_UNIT_TEST_SUITE(TLazyValueTestSuite) { Y_UNIT_TEST(TestLazyValueCopyValueInitialization) { size_t numCopies = 0; TCopyCounter counter{numCopies}; - TLazyValue<TCopyCounter> value{[&counter]() { return counter; }}; + TLazyValue<TCopyCounter> value{[&counter]() { return counter; }}; UNIT_ASSERT_EQUAL(numCopies, 0); value.InitDefault(); UNIT_ASSERT_EQUAL(numCopies, 1); diff --git a/util/generic/list.cpp b/util/generic/list.cpp index 9c81b49c44..471c2a14b7 100644 --- a/util/generic/list.cpp +++ b/util/generic/list.cpp @@ -1 +1 @@ -#include "list.h" +#include "list.h" diff --git a/util/generic/list.h b/util/generic/list.h index 9aeb7b8a7b..7b0b8ffc72 100644 --- a/util/generic/list.h +++ b/util/generic/list.h @@ -1,22 +1,22 @@ #pragma once - + #include "fwd.h" -#include <util/memory/alloc.h> - +#include <util/memory/alloc.h> + #include <initializer_list> -#include <list> +#include <list> #include <memory> #include <utility> - + template <class T, class A> class TList: public std::list<T, TReboundAllocator<A, T>> { using TBase = std::list<T, TReboundAllocator<A, T>>; - + public: using TBase::TBase; - - inline explicit operator bool() const noexcept { - return !this->empty(); - } -}; + + inline explicit operator bool() const noexcept { + return !this->empty(); + } +}; diff --git a/util/generic/map.cpp b/util/generic/map.cpp index a8fa3b1325..b323fbb46d 100644 --- a/util/generic/map.cpp +++ b/util/generic/map.cpp @@ -1 +1 @@ -#include "map.h" +#include "map.h" diff --git a/util/generic/map.h b/util/generic/map.h index 0af167650b..b5001b56c0 100644 --- a/util/generic/map.h +++ b/util/generic/map.h @@ -2,22 +2,22 @@ #include "fwd.h" #include "mapfindptr.h" - + #include <util/str_stl.h> -#include <util/memory/alloc.h> +#include <util/memory/alloc.h> #include <utility> #include <initializer_list> -#include <map> +#include <map> #include <memory> - + template <class K, class V, class Less, class A> class TMap: public std::map<K, V, Less, TReboundAllocator<A, std::pair<const K, V>>>, public TMapOps<TMap<K, V, Less, A>> { using TBase = std::map<K, V, Less, TReboundAllocator<A, std::pair<const K, V>>>; - -public: + +public: using TBase::TBase; - + inline explicit operator bool() const noexcept { return !this->empty(); } @@ -30,10 +30,10 @@ public: template <class K, class V, class Less, class A> class TMultiMap: public std::multimap<K, V, Less, TReboundAllocator<A, std::pair<const K, V>>> { using TBase = std::multimap<K, V, Less, TReboundAllocator<A, std::pair<const K, V>>>; - -public: + +public: using TBase::TBase; - + inline explicit operator bool() const noexcept { return !this->empty(); } diff --git a/util/generic/map_ut.cpp b/util/generic/map_ut.cpp index 8b7eed0598..79e832b024 100644 --- a/util/generic/map_ut.cpp +++ b/util/generic/map_ut.cpp @@ -1,15 +1,15 @@ -#include "map.h" - +#include "map.h" + #include <library/cpp/testing/unittest/registar.h> #include <util/memory/pool.h> -#include <algorithm> - +#include <algorithm> + Y_UNIT_TEST_SUITE(TYMapTest) { template <typename TAlloc> - void DoTestMap1(TMap<char, int, TLess<char>, TAlloc>& m); + void DoTestMap1(TMap<char, int, TLess<char>, TAlloc>& m); template <typename TAlloc> - void DoTestMMap1(TMultiMap<char, int, TLess<char>, TAlloc>& mm); + void DoTestMMap1(TMultiMap<char, int, TLess<char>, TAlloc>& mm); Y_UNIT_TEST(TestMap1) { { @@ -35,373 +35,373 @@ Y_UNIT_TEST_SUITE(TYMapTest) { } } - template <typename TAlloc> - void DoTestMap1(TMap<char, int, TLess<char>, TAlloc>& m) { + template <typename TAlloc> + void DoTestMap1(TMap<char, int, TLess<char>, TAlloc>& m) { using maptype = TMap<char, int, TLess<char>, TAlloc>; - // Store mappings between roman numerals and decimals. - m['l'] = 50; - m['x'] = 20; // Deliberate mistake. - m['v'] = 5; - m['i'] = 1; - - UNIT_ASSERT(m['x'] == 20); - m['x'] = 10; // Correct mistake. - UNIT_ASSERT(m['x'] == 10); - UNIT_ASSERT(m['z'] == 0); - - UNIT_ASSERT(m.count('z') == 1); - + // Store mappings between roman numerals and decimals. + m['l'] = 50; + m['x'] = 20; // Deliberate mistake. + m['v'] = 5; + m['i'] = 1; + + UNIT_ASSERT(m['x'] == 20); + m['x'] = 10; // Correct mistake. + UNIT_ASSERT(m['x'] == 10); + UNIT_ASSERT(m['z'] == 0); + + UNIT_ASSERT(m.count('z') == 1); + std::pair<typename maptype::iterator, bool> p = m.insert(std::pair<const char, int>('c', 100)); - - UNIT_ASSERT(p.second); - UNIT_ASSERT(p.first != m.end()); - UNIT_ASSERT((*p.first).first == 'c'); - UNIT_ASSERT((*p.first).second == 100); - + + UNIT_ASSERT(p.second); + UNIT_ASSERT(p.first != m.end()); + UNIT_ASSERT((*p.first).first == 'c'); + UNIT_ASSERT((*p.first).second == 100); + p = m.insert(std::pair<const char, int>('c', 100)); - - UNIT_ASSERT(!p.second); // already existing pair - UNIT_ASSERT(p.first != m.end()); - UNIT_ASSERT((*p.first).first == 'c'); - UNIT_ASSERT((*p.first).second == 100); - } - - template <typename TAlloc> - void DoTestMMap1(TMultiMap<char, int, TLess<char>, TAlloc>& m) { + + UNIT_ASSERT(!p.second); // already existing pair + UNIT_ASSERT(p.first != m.end()); + UNIT_ASSERT((*p.first).first == 'c'); + UNIT_ASSERT((*p.first).second == 100); + } + + template <typename TAlloc> + void DoTestMMap1(TMultiMap<char, int, TLess<char>, TAlloc>& m) { using mmap = TMultiMap<char, int, TLess<char>, TAlloc>; - UNIT_ASSERT(m.count('X') == 0); - + UNIT_ASSERT(m.count('X') == 0); + m.insert(std::pair<const char, int>('X', 10)); // Standard way. - UNIT_ASSERT(m.count('X') == 1); - + UNIT_ASSERT(m.count('X') == 1); + m.insert(std::pair<const char, int>('X', 20)); // jbuck: standard way - UNIT_ASSERT(m.count('X') == 2); - + UNIT_ASSERT(m.count('X') == 2); + m.insert(std::pair<const char, int>('Y', 32)); // jbuck: standard way - typename mmap::iterator i = m.find('X'); // Find first match. + typename mmap::iterator i = m.find('X'); // Find first match. ++i; - UNIT_ASSERT((*i).first == 'X'); - UNIT_ASSERT((*i).second == 20); + UNIT_ASSERT((*i).first == 'X'); + UNIT_ASSERT((*i).second == 20); ++i; - UNIT_ASSERT((*i).first == 'Y'); - UNIT_ASSERT((*i).second == 32); + UNIT_ASSERT((*i).first == 'Y'); + UNIT_ASSERT((*i).second == 32); ++i; - UNIT_ASSERT(i == m.end()); - - size_t count = m.erase('X'); - UNIT_ASSERT(count == 2); - } - + UNIT_ASSERT(i == m.end()); + + size_t count = m.erase('X'); + UNIT_ASSERT(count == 2); + } + Y_UNIT_TEST(TestMMap2) { using pair_type = std::pair<const int, char>; - - pair_type p1(3, 'c'); - pair_type p2(6, 'f'); - pair_type p3(1, 'a'); - pair_type p4(2, 'b'); - pair_type p5(3, 'x'); - pair_type p6(6, 'f'); - + + pair_type p1(3, 'c'); + pair_type p2(6, 'f'); + pair_type p3(1, 'a'); + pair_type p4(2, 'b'); + pair_type p5(3, 'x'); + pair_type p6(6, 'f'); + using mmap = TMultiMap<int, char, TLess<int>>; - - pair_type array[] = { - p1, - p2, - p3, - p4, - p5, - p6}; - - mmap m(array + 0, array + 6); - mmap::iterator i; - i = m.lower_bound(3); - UNIT_ASSERT((*i).first == 3); - UNIT_ASSERT((*i).second == 'c'); - - i = m.upper_bound(3); - UNIT_ASSERT((*i).first == 6); - UNIT_ASSERT((*i).second == 'f'); - } - + + pair_type array[] = { + p1, + p2, + p3, + p4, + p5, + p6}; + + mmap m(array + 0, array + 6); + mmap::iterator i; + i = m.lower_bound(3); + UNIT_ASSERT((*i).first == 3); + UNIT_ASSERT((*i).second == 'c'); + + i = m.upper_bound(3); + UNIT_ASSERT((*i).first == 6); + UNIT_ASSERT((*i).second == 'f'); + } + Y_UNIT_TEST(TestIterators) { using int_map = TMap<int, char, TLess<int>>; - int_map imap; - - { - int_map::iterator ite(imap.begin()); - int_map::const_iterator cite(imap.begin()); - - UNIT_ASSERT(ite == cite); - UNIT_ASSERT(!(ite != cite)); - UNIT_ASSERT(cite == ite); - UNIT_ASSERT(!(cite != ite)); - } - + int_map imap; + + { + int_map::iterator ite(imap.begin()); + int_map::const_iterator cite(imap.begin()); + + UNIT_ASSERT(ite == cite); + UNIT_ASSERT(!(ite != cite)); + UNIT_ASSERT(cite == ite); + UNIT_ASSERT(!(cite != ite)); + } + using mmap = TMultiMap<int, char, TLess<int>>; using pair_type = mmap::value_type; - - pair_type p1(3, 'c'); - pair_type p2(6, 'f'); - pair_type p3(1, 'a'); - pair_type p4(2, 'b'); - pair_type p5(3, 'x'); - pair_type p6(6, 'f'); - - pair_type array[] = { - p1, - p2, - p3, - p4, - p5, - p6}; - - mmap m(array + 0, array + 6); - - { - mmap::iterator ite(m.begin()); - mmap::const_iterator cite(m.begin()); - //test compare between const_iterator and iterator - UNIT_ASSERT(ite == cite); - UNIT_ASSERT(!(ite != cite)); - UNIT_ASSERT(cite == ite); - UNIT_ASSERT(!(cite != ite)); - } - - mmap::reverse_iterator ri = m.rbegin(); - - UNIT_ASSERT(ri != m.rend()); - UNIT_ASSERT(ri == m.rbegin()); - UNIT_ASSERT((*ri).first == 6); - UNIT_ASSERT((*ri++).second == 'f'); - UNIT_ASSERT((*ri).first == 6); - UNIT_ASSERT((*ri).second == 'f'); - - mmap const& cm = m; - mmap::const_reverse_iterator rci = cm.rbegin(); - - UNIT_ASSERT(rci != cm.rend()); - UNIT_ASSERT((*rci).first == 6); - UNIT_ASSERT((*rci++).second == 'f'); - UNIT_ASSERT((*rci).first == 6); - UNIT_ASSERT((*rci).second == 'f'); - } - + + pair_type p1(3, 'c'); + pair_type p2(6, 'f'); + pair_type p3(1, 'a'); + pair_type p4(2, 'b'); + pair_type p5(3, 'x'); + pair_type p6(6, 'f'); + + pair_type array[] = { + p1, + p2, + p3, + p4, + p5, + p6}; + + mmap m(array + 0, array + 6); + + { + mmap::iterator ite(m.begin()); + mmap::const_iterator cite(m.begin()); + //test compare between const_iterator and iterator + UNIT_ASSERT(ite == cite); + UNIT_ASSERT(!(ite != cite)); + UNIT_ASSERT(cite == ite); + UNIT_ASSERT(!(cite != ite)); + } + + mmap::reverse_iterator ri = m.rbegin(); + + UNIT_ASSERT(ri != m.rend()); + UNIT_ASSERT(ri == m.rbegin()); + UNIT_ASSERT((*ri).first == 6); + UNIT_ASSERT((*ri++).second == 'f'); + UNIT_ASSERT((*ri).first == 6); + UNIT_ASSERT((*ri).second == 'f'); + + mmap const& cm = m; + mmap::const_reverse_iterator rci = cm.rbegin(); + + UNIT_ASSERT(rci != cm.rend()); + UNIT_ASSERT((*rci).first == 6); + UNIT_ASSERT((*rci++).second == 'f'); + UNIT_ASSERT((*rci).first == 6); + UNIT_ASSERT((*rci).second == 'f'); + } + Y_UNIT_TEST(TestEqualRange) { using maptype = TMap<char, int, TLess<char>>; - - { - maptype m; - m['x'] = 10; - + + { + maptype m; + m['x'] = 10; + std::pair<maptype::iterator, maptype::iterator> ret; - ret = m.equal_range('x'); - UNIT_ASSERT(ret.first != ret.second); - UNIT_ASSERT((*(ret.first)).first == 'x'); - UNIT_ASSERT((*(ret.first)).second == 10); - UNIT_ASSERT(++(ret.first) == ret.second); - } - - { - { - maptype m; - - maptype::iterator i = m.lower_bound('x'); - UNIT_ASSERT(i == m.end()); - - i = m.upper_bound('x'); - UNIT_ASSERT(i == m.end()); - + ret = m.equal_range('x'); + UNIT_ASSERT(ret.first != ret.second); + UNIT_ASSERT((*(ret.first)).first == 'x'); + UNIT_ASSERT((*(ret.first)).second == 10); + UNIT_ASSERT(++(ret.first) == ret.second); + } + + { + { + maptype m; + + maptype::iterator i = m.lower_bound('x'); + UNIT_ASSERT(i == m.end()); + + i = m.upper_bound('x'); + UNIT_ASSERT(i == m.end()); + std::pair<maptype::iterator, maptype::iterator> ret; - ret = m.equal_range('x'); - UNIT_ASSERT(ret.first == ret.second); - UNIT_ASSERT(ret.first == m.end()); - } - - { - const maptype m; + ret = m.equal_range('x'); + UNIT_ASSERT(ret.first == ret.second); + UNIT_ASSERT(ret.first == m.end()); + } + + { + const maptype m; std::pair<maptype::const_iterator, maptype::const_iterator> ret; - ret = m.equal_range('x'); - UNIT_ASSERT(ret.first == ret.second); - UNIT_ASSERT(ret.first == m.end()); - } - } - } - - struct TKey { - TKey() - : m_data(0) - { - } - - explicit TKey(int data) - : m_data(data) - { - } - - int m_data; - }; - - struct TKeyCmp { - bool operator()(TKey lhs, TKey rhs) const { - return lhs.m_data < rhs.m_data; - } - - bool operator()(TKey lhs, int rhs) const { - return lhs.m_data < rhs; - } - - bool operator()(int lhs, TKey rhs) const { - return lhs < rhs.m_data; - } + ret = m.equal_range('x'); + UNIT_ASSERT(ret.first == ret.second); + UNIT_ASSERT(ret.first == m.end()); + } + } + } + + struct TKey { + TKey() + : m_data(0) + { + } + + explicit TKey(int data) + : m_data(data) + { + } + + int m_data; + }; + + struct TKeyCmp { + bool operator()(TKey lhs, TKey rhs) const { + return lhs.m_data < rhs.m_data; + } + + bool operator()(TKey lhs, int rhs) const { + return lhs.m_data < rhs; + } + + bool operator()(int lhs, TKey rhs) const { + return lhs < rhs.m_data; + } using is_transparent = void; - }; - - struct TKeyCmpPtr { - bool operator()(TKey const volatile* lhs, TKey const volatile* rhs) const { - return (*lhs).m_data < (*rhs).m_data; - } - - bool operator()(TKey const volatile* lhs, int rhs) const { - return (*lhs).m_data < rhs; - } - - bool operator()(int lhs, TKey const volatile* rhs) const { - return lhs < (*rhs).m_data; - } + }; + + struct TKeyCmpPtr { + bool operator()(TKey const volatile* lhs, TKey const volatile* rhs) const { + return (*lhs).m_data < (*rhs).m_data; + } + + bool operator()(TKey const volatile* lhs, int rhs) const { + return (*lhs).m_data < rhs; + } + + bool operator()(int lhs, TKey const volatile* rhs) const { + return lhs < (*rhs).m_data; + } using is_transparent = void; - }; - + }; + Y_UNIT_TEST(TestTemplateMethods) { - { + { using Container = TMap<TKey, int, TKeyCmp>; using value = Container::value_type; - - Container cont; - - cont.insert(value(TKey(1), 1)); - cont.insert(value(TKey(2), 2)); - cont.insert(value(TKey(3), 3)); - cont.insert(value(TKey(4), 4)); - - UNIT_ASSERT(cont.count(TKey(1)) == 1); - UNIT_ASSERT(cont.count(1) == 1); - UNIT_ASSERT(cont.count(5) == 0); - - UNIT_ASSERT(cont.find(2) != cont.end()); - UNIT_ASSERT(cont.lower_bound(2) != cont.end()); - UNIT_ASSERT(cont.upper_bound(2) != cont.end()); - UNIT_ASSERT(cont.equal_range(2) != std::make_pair(cont.begin(), cont.end())); - - Container const& ccont = cont; - - UNIT_ASSERT(ccont.find(2) != ccont.end()); - UNIT_ASSERT(ccont.lower_bound(2) != ccont.end()); - UNIT_ASSERT(ccont.upper_bound(2) != ccont.end()); - UNIT_ASSERT(ccont.equal_range(2) != std::make_pair(ccont.end(), ccont.end())); - } - - { + + Container cont; + + cont.insert(value(TKey(1), 1)); + cont.insert(value(TKey(2), 2)); + cont.insert(value(TKey(3), 3)); + cont.insert(value(TKey(4), 4)); + + UNIT_ASSERT(cont.count(TKey(1)) == 1); + UNIT_ASSERT(cont.count(1) == 1); + UNIT_ASSERT(cont.count(5) == 0); + + UNIT_ASSERT(cont.find(2) != cont.end()); + UNIT_ASSERT(cont.lower_bound(2) != cont.end()); + UNIT_ASSERT(cont.upper_bound(2) != cont.end()); + UNIT_ASSERT(cont.equal_range(2) != std::make_pair(cont.begin(), cont.end())); + + Container const& ccont = cont; + + UNIT_ASSERT(ccont.find(2) != ccont.end()); + UNIT_ASSERT(ccont.lower_bound(2) != ccont.end()); + UNIT_ASSERT(ccont.upper_bound(2) != ccont.end()); + UNIT_ASSERT(ccont.equal_range(2) != std::make_pair(ccont.end(), ccont.end())); + } + + { using Container = TMap<TKey*, int, TKeyCmpPtr>; using value = Container::value_type; - - Container cont; - - TKey key1(1), key2(2), key3(3), key4(4); - - cont.insert(value(&key1, 1)); - cont.insert(value(&key2, 2)); - cont.insert(value(&key3, 3)); - cont.insert(value(&key4, 4)); - - UNIT_ASSERT(cont.count(1) == 1); - UNIT_ASSERT(cont.count(5) == 0); - - UNIT_ASSERT(cont.find(2) != cont.end()); - UNIT_ASSERT(cont.lower_bound(2) != cont.end()); - UNIT_ASSERT(cont.upper_bound(2) != cont.end()); - UNIT_ASSERT(cont.equal_range(2) != std::make_pair(cont.begin(), cont.end())); - - Container const& ccont = cont; - - UNIT_ASSERT(ccont.find(2) != ccont.end()); - UNIT_ASSERT(ccont.lower_bound(2) != ccont.end()); - UNIT_ASSERT(ccont.upper_bound(2) != ccont.end()); - UNIT_ASSERT(ccont.equal_range(2) != std::make_pair(ccont.begin(), ccont.end())); - } - - { + + Container cont; + + TKey key1(1), key2(2), key3(3), key4(4); + + cont.insert(value(&key1, 1)); + cont.insert(value(&key2, 2)); + cont.insert(value(&key3, 3)); + cont.insert(value(&key4, 4)); + + UNIT_ASSERT(cont.count(1) == 1); + UNIT_ASSERT(cont.count(5) == 0); + + UNIT_ASSERT(cont.find(2) != cont.end()); + UNIT_ASSERT(cont.lower_bound(2) != cont.end()); + UNIT_ASSERT(cont.upper_bound(2) != cont.end()); + UNIT_ASSERT(cont.equal_range(2) != std::make_pair(cont.begin(), cont.end())); + + Container const& ccont = cont; + + UNIT_ASSERT(ccont.find(2) != ccont.end()); + UNIT_ASSERT(ccont.lower_bound(2) != ccont.end()); + UNIT_ASSERT(ccont.upper_bound(2) != ccont.end()); + UNIT_ASSERT(ccont.equal_range(2) != std::make_pair(ccont.begin(), ccont.end())); + } + + { using Container = TMultiMap<TKey, int, TKeyCmp>; using value = Container::value_type; - - Container cont; - - cont.insert(value(TKey(1), 1)); - cont.insert(value(TKey(2), 2)); - cont.insert(value(TKey(3), 3)); - cont.insert(value(TKey(4), 4)); - - UNIT_ASSERT(cont.count(TKey(1)) == 1); - UNIT_ASSERT(cont.count(1) == 1); - UNIT_ASSERT(cont.count(5) == 0); - - UNIT_ASSERT(cont.find(2) != cont.end()); - UNIT_ASSERT(cont.lower_bound(2) != cont.end()); - UNIT_ASSERT(cont.upper_bound(2) != cont.end()); - UNIT_ASSERT(cont.equal_range(2) != std::make_pair(cont.begin(), cont.end())); - - Container const& ccont = cont; - - UNIT_ASSERT(ccont.find(2) != ccont.end()); - UNIT_ASSERT(ccont.lower_bound(2) != ccont.end()); - UNIT_ASSERT(ccont.upper_bound(2) != ccont.end()); + + Container cont; + + cont.insert(value(TKey(1), 1)); + cont.insert(value(TKey(2), 2)); + cont.insert(value(TKey(3), 3)); + cont.insert(value(TKey(4), 4)); + + UNIT_ASSERT(cont.count(TKey(1)) == 1); + UNIT_ASSERT(cont.count(1) == 1); + UNIT_ASSERT(cont.count(5) == 0); + + UNIT_ASSERT(cont.find(2) != cont.end()); + UNIT_ASSERT(cont.lower_bound(2) != cont.end()); + UNIT_ASSERT(cont.upper_bound(2) != cont.end()); + UNIT_ASSERT(cont.equal_range(2) != std::make_pair(cont.begin(), cont.end())); + + Container const& ccont = cont; + + UNIT_ASSERT(ccont.find(2) != ccont.end()); + UNIT_ASSERT(ccont.lower_bound(2) != ccont.end()); + UNIT_ASSERT(ccont.upper_bound(2) != ccont.end()); UNIT_ASSERT(ccont.equal_range(2) != std::make_pair(ccont.end(), ccont.end())); - } - - { + } + + { using Container = TMultiMap<TKey const volatile*, int, TKeyCmpPtr>; using value = Container::value_type; - - Container cont; - - TKey key1(1), key2(2), key3(3), key4(4); - - cont.insert(value(&key1, 1)); - cont.insert(value(&key2, 2)); - cont.insert(value(&key3, 3)); - cont.insert(value(&key4, 4)); - - UNIT_ASSERT(cont.count(1) == 1); - UNIT_ASSERT(cont.count(5) == 0); - - UNIT_ASSERT(cont.find(2) != cont.end()); - UNIT_ASSERT(cont.lower_bound(2) != cont.end()); - UNIT_ASSERT(cont.upper_bound(2) != cont.end()); - UNIT_ASSERT(cont.equal_range(2) != std::make_pair(cont.begin(), cont.end())); - - Container const& ccont = cont; - - UNIT_ASSERT(ccont.find(2) != ccont.end()); - UNIT_ASSERT(ccont.lower_bound(2) != ccont.end()); - UNIT_ASSERT(ccont.upper_bound(2) != ccont.end()); - UNIT_ASSERT(ccont.equal_range(2) != std::make_pair(ccont.begin(), ccont.end())); - } - } - - template <typename T> - static void EmptyAndInsertTest(typename T::value_type v) { - T c; - UNIT_ASSERT(!c); - c.insert(v); - UNIT_ASSERT(c); - } + + Container cont; + + TKey key1(1), key2(2), key3(3), key4(4); + + cont.insert(value(&key1, 1)); + cont.insert(value(&key2, 2)); + cont.insert(value(&key3, 3)); + cont.insert(value(&key4, 4)); + + UNIT_ASSERT(cont.count(1) == 1); + UNIT_ASSERT(cont.count(5) == 0); + + UNIT_ASSERT(cont.find(2) != cont.end()); + UNIT_ASSERT(cont.lower_bound(2) != cont.end()); + UNIT_ASSERT(cont.upper_bound(2) != cont.end()); + UNIT_ASSERT(cont.equal_range(2) != std::make_pair(cont.begin(), cont.end())); + + Container const& ccont = cont; + + UNIT_ASSERT(ccont.find(2) != ccont.end()); + UNIT_ASSERT(ccont.lower_bound(2) != ccont.end()); + UNIT_ASSERT(ccont.upper_bound(2) != ccont.end()); + UNIT_ASSERT(ccont.equal_range(2) != std::make_pair(ccont.begin(), ccont.end())); + } + } + + template <typename T> + static void EmptyAndInsertTest(typename T::value_type v) { + T c; + UNIT_ASSERT(!c); + c.insert(v); + UNIT_ASSERT(c); + } Y_UNIT_TEST(TestEmpty) { EmptyAndInsertTest<TMap<char, int, TLess<char>>>(std::pair<char, int>('a', 1)); EmptyAndInsertTest<TMultiMap<char, int, TLess<char>>>(std::pair<char, int>('a', 1)); - } + } struct TParametrizedKeyCmp { bool Inverse; diff --git a/util/generic/mapfindptr.cpp b/util/generic/mapfindptr.cpp index 3dcacb87d0..5e3ff4b779 100644 --- a/util/generic/mapfindptr.cpp +++ b/util/generic/mapfindptr.cpp @@ -1 +1 @@ -#include "mapfindptr.h" +#include "mapfindptr.h" diff --git a/util/generic/mapfindptr.h b/util/generic/mapfindptr.h index 38c380f5e6..bc10cac60f 100644 --- a/util/generic/mapfindptr.h +++ b/util/generic/mapfindptr.h @@ -10,29 +10,29 @@ if (T* value = MapFindPtr(myMap, someKey) { */ -template <class Map, class K> +template <class Map, class K> inline auto MapFindPtr(Map& map, const K& key) { - auto i = map.find(key); - + auto i = map.find(key); + return (i == map.end() ? nullptr : &i->second); } -template <class Map, class K> +template <class Map, class K> inline auto MapFindPtr(const Map& map, const K& key) { - auto i = map.find(key); - + auto i = map.find(key); + return (i == map.end() ? nullptr : &i->second); } /** helper for THashMap/TMap */ template <class Derived> struct TMapOps { - template <class K> + template <class K> inline auto FindPtr(const K& key) { return MapFindPtr(static_cast<Derived&>(*this), key); } - - template <class K> + + template <class K> inline auto FindPtr(const K& key) const { return MapFindPtr(static_cast<const Derived&>(*this), key); } diff --git a/util/generic/mapfindptr_ut.cpp b/util/generic/mapfindptr_ut.cpp index 53f0f04b38..613da7a96b 100644 --- a/util/generic/mapfindptr_ut.cpp +++ b/util/generic/mapfindptr_ut.cpp @@ -1,47 +1,47 @@ #include "string.h" -#include "hash.h" - +#include "hash.h" + #include <library/cpp/testing/unittest/registar.h> -#include <map> - -#include "mapfindptr.h" - +#include <map> + +#include "mapfindptr.h" + Y_UNIT_TEST_SUITE(TMapFindPtrTest) { - struct TTestMap: std::map<int, TString>, TMapOps<TTestMap> {}; + struct TTestMap: std::map<int, TString>, TMapOps<TTestMap> {}; Y_UNIT_TEST(TestDerivedClass) { - TTestMap a; + TTestMap a; - a[42] = "cat"; + a[42] = "cat"; UNIT_ASSERT(a.FindPtr(42)); - UNIT_ASSERT_EQUAL(*a.FindPtr(42), "cat"); + UNIT_ASSERT_EQUAL(*a.FindPtr(42), "cat"); UNIT_ASSERT_EQUAL(a.FindPtr(0), nullptr); - //test mutation + //test mutation if (TString* p = a.FindPtr(42)) { - *p = "dog"; + *p = "dog"; } UNIT_ASSERT(a.FindPtr(42)); - UNIT_ASSERT_EQUAL(*a.FindPtr(42), "dog"); - - //test const-overloaded functions too - const TTestMap& b = a; - UNIT_ASSERT(b.FindPtr(42) && *b.FindPtr(42) == "dog"); + UNIT_ASSERT_EQUAL(*a.FindPtr(42), "dog"); + + //test const-overloaded functions too + const TTestMap& b = a; + UNIT_ASSERT(b.FindPtr(42) && *b.FindPtr(42) == "dog"); UNIT_ASSERT_EQUAL(b.FindPtr(0), nullptr); UNIT_ASSERT_STRINGS_EQUAL(b.Value(42, "cat"), "dog"); UNIT_ASSERT_STRINGS_EQUAL(b.Value(0, "alien"), "alien"); - } - + } + Y_UNIT_TEST(TestTemplateFind) { THashMap<TString, int> m; - + m[TString("x")] = 2; - + UNIT_ASSERT(m.FindPtr(TStringBuf("x"))); UNIT_ASSERT_EQUAL(*m.FindPtr(TStringBuf("x")), 2); - } + } Y_UNIT_TEST(TestValue) { TTestMap a; diff --git a/util/generic/maybe.cpp b/util/generic/maybe.cpp index e1df937a8b..43262934f8 100644 --- a/util/generic/maybe.cpp +++ b/util/generic/maybe.cpp @@ -1,4 +1,4 @@ -#include "maybe.h" +#include "maybe.h" #include <util/system/type_name.h> [[noreturn]] void NMaybe::TPolicyUndefinedExcept::OnEmpty(const std::type_info& valueTypeInfo) { diff --git a/util/generic/maybe.h b/util/generic/maybe.h index 705f64e413..34d21aebcd 100644 --- a/util/generic/maybe.h +++ b/util/generic/maybe.h @@ -3,12 +3,12 @@ #include <utility> #include "maybe_traits.h" -#include "yexception.h" - -#include <util/system/align.h> +#include "yexception.h" + +#include <util/system/align.h> #include <util/stream/output.h> #include <util/ysaveload.h> - + namespace NMaybe { struct TPolicyUndefinedExcept { [[noreturn]] static void OnEmpty(const std::type_info& valueTypeInfo); @@ -20,8 +20,8 @@ namespace NMaybe { } struct TNothing { - explicit constexpr TNothing(int) noexcept { - } + explicit constexpr TNothing(int) noexcept { + } }; constexpr TNothing NothingObject{0}; @@ -35,7 +35,7 @@ constexpr bool operator==(TNothing, TNothing) noexcept { } template <class T, class Policy /*= ::NMaybe::TPolicyUndefinedExcept*/> -class TMaybe: private TMaybeBase<T> { +class TMaybe: private TMaybeBase<T> { public: using TInPlace = NMaybe::TInPlace; @@ -115,9 +115,9 @@ private: template <class U> struct TMoveAssignable { public: - static constexpr bool value = std::is_constructible<T, U&&>::value && - std::is_assignable<T&, U&&>::value && - !TAssignableFromMaybeSomehow<U>::value; + static constexpr bool value = std::is_constructible<T, U&&>::value && + std::is_assignable<T&, U&&>::value && + !TAssignableFromMaybeSomehow<U>::value; }; template <class U> @@ -164,18 +164,18 @@ public: template <class... Args> constexpr explicit TMaybe(TInPlace, Args&&... args) - : TBase(TInPlace{}, std::forward<Args>(args)...) - { - } + : TBase(TInPlace{}, std::forward<Args>(args)...) + { + } template <class U, class... TArgs> constexpr explicit TMaybe(TInPlace, std::initializer_list<U> il, TArgs&&... args) - : TBase(TInPlace{}, il, std::forward<TArgs>(args)...) - { - } + : TBase(TInPlace{}, il, std::forward<TArgs>(args)...) + { + } - constexpr TMaybe(TNothing) noexcept { - } + constexpr TMaybe(TNothing) noexcept { + } template <class U, class = std::enable_if_t<TImplicitCopyCtor<U>::value>> TMaybe(const TMaybe<U, Policy>& right) { @@ -211,21 +211,21 @@ public: template <class U = T, class = std::enable_if_t<TImplicitAnyCtor<U>::value>> constexpr TMaybe(U&& right) - : TBase(TInPlace{}, std::forward<U>(right)) - { - } + : TBase(TInPlace{}, std::forward<U>(right)) + { + } template <class U = T, std::enable_if_t<TExplicitAnyCtor<U>::value, bool> = false> constexpr explicit TMaybe(U&& right) - : TBase(TInPlace{}, std::forward<U>(right)) - { - } + : TBase(TInPlace{}, std::forward<U>(right)) + { + } ~TMaybe() = default; constexpr TMaybe& operator=(const TMaybe&) = default; constexpr TMaybe& operator=(TMaybe&&) = default; - + TMaybe& operator=(TNothing) noexcept { Clear(); return *this; @@ -243,8 +243,8 @@ public: template <class U> std::enable_if_t<TCopyAssignable<U>::value, - TMaybe&> - operator=(const TMaybe<U, Policy>& right) { + TMaybe&> + operator=(const TMaybe<U, Policy>& right) { if (right.Defined()) { if (Defined()) { *Data() = right.GetRef(); @@ -260,9 +260,9 @@ public: template <class U> std::enable_if_t<TMoveAssignable<U>::value, - TMaybe&> - operator=(TMaybe<U, Policy>&& right) noexcept( - std::is_nothrow_assignable<T&, U&&>::value&& std::is_nothrow_constructible<T, U&&>::value) + TMaybe&> + operator=(TMaybe<U, Policy>&& right) noexcept( + std::is_nothrow_assignable<T&, U&&>::value&& std::is_nothrow_constructible<T, U&&>::value) { if (right.Defined()) { if (Defined()) { @@ -295,7 +295,7 @@ public: return this->Defined_; } - Y_PURE_FUNCTION constexpr bool Empty() const noexcept { + Y_PURE_FUNCTION constexpr bool Empty() const noexcept { return !Defined(); } @@ -315,13 +315,13 @@ public: constexpr const T& GetRef() const& { CheckDefined(); - + return *Data(); } constexpr T& GetRef() & { CheckDefined(); - + return *Data(); } @@ -388,9 +388,9 @@ public: void Save(IOutputStream* out) const { const bool defined = Defined(); - + ::Save<bool>(out, defined); - + if (defined) { ::Save(out, *Data()); } @@ -398,14 +398,14 @@ public: void Load(IInputStream* in) { bool defined; - + ::Load(in, defined); - + if (defined) { if (!Defined()) { ConstructInPlace(); } - + ::Load(in, *Data()); } else { Clear(); @@ -441,7 +441,7 @@ private: return std::addressof(this->Data_); } - template <typename... Args> + template <typename... Args> void Init(Args&&... args) { new (Data()) T(std::forward<Args>(args)...); this->Defined_ = true; @@ -486,12 +486,12 @@ struct THash<TMaybe<T, TPolicy>> { // Comparisons between TMaybe template <class T, class TPolicy> constexpr bool operator==(const ::TMaybe<T, TPolicy>& left, const ::TMaybe<T, TPolicy>& right) { - return (static_cast<bool>(left) != static_cast<bool>(right)) - ? false - : ( - !static_cast<bool>(left) - ? true - : *left == *right); + return (static_cast<bool>(left) != static_cast<bool>(right)) + ? false + : ( + !static_cast<bool>(left) + ? true + : *left == *right); } template <class T, class TPolicy> @@ -502,11 +502,11 @@ constexpr bool operator!=(const TMaybe<T, TPolicy>& left, const TMaybe<T, TPolic template <class T, class TPolicy> constexpr bool operator<(const TMaybe<T, TPolicy>& left, const TMaybe<T, TPolicy>& right) { return (!static_cast<bool>(right)) - ? false - : ( - !static_cast<bool>(left) - ? true - : (*left < *right)); + ? false + : ( + !static_cast<bool>(left) + ? true + : (*left < *right)); } template <class T, class TPolicy> diff --git a/util/generic/maybe_traits.h b/util/generic/maybe_traits.h index c7f2fed3e7..9e9f56955e 100644 --- a/util/generic/maybe_traits.h +++ b/util/generic/maybe_traits.h @@ -10,16 +10,16 @@ namespace NMaybe { template <class T, bool = std::is_trivially_destructible<T>::value> struct TStorageBase { constexpr TStorageBase() noexcept - : NullState_('\0') - { - } + : NullState_('\0') + { + } template <class... Args> constexpr TStorageBase(TInPlace, Args&&... args) : Data_(std::forward<Args>(args)...) - , Defined_(true) - { - } + , Defined_(true) + { + } ~TStorageBase() = default; @@ -33,16 +33,16 @@ namespace NMaybe { template <class T> struct TStorageBase<T, false> { constexpr TStorageBase() noexcept - : NullState_('\0') - { - } + : NullState_('\0') + { + } template <class... Args> constexpr TStorageBase(TInPlace, Args&&... args) : Data_(std::forward<Args>(args)...) - , Defined_(true) - { - } + , Defined_(true) + { + } ~TStorageBase() { if (this->Defined_) { @@ -60,12 +60,12 @@ namespace NMaybe { // -------------------- COPY CONSTRUCT -------------------- template <class T, bool = std::is_trivially_copy_constructible<T>::value> - struct TCopyBase: TStorageBase<T> { + struct TCopyBase: TStorageBase<T> { using TStorageBase<T>::TStorageBase; }; template <class T> - struct TCopyBase<T, false>: TStorageBase<T> { + struct TCopyBase<T, false>: TStorageBase<T> { using TStorageBase<T>::TStorageBase; constexpr TCopyBase() = default; @@ -83,12 +83,12 @@ namespace NMaybe { // -------------------- MOVE CONSTRUCT -------------------- template <class T, bool = std::is_trivially_move_constructible<T>::value> - struct TMoveBase: TCopyBase<T> { + struct TMoveBase: TCopyBase<T> { using TCopyBase<T>::TCopyBase; }; template <class T> - struct TMoveBase<T, false>: TCopyBase<T> { + struct TMoveBase<T, false>: TCopyBase<T> { using TCopyBase<T>::TCopyBase; constexpr TMoveBase() noexcept = default; @@ -106,12 +106,12 @@ namespace NMaybe { // -------------------- COPY ASSIGN -------------------- template <class T, bool = std::is_trivially_copy_assignable<T>::value> - struct TCopyAssignBase: TMoveBase<T> { + struct TCopyAssignBase: TMoveBase<T> { using TMoveBase<T>::TMoveBase; }; template <class T> - struct TCopyAssignBase<T, false>: TMoveBase<T> { + struct TCopyAssignBase<T, false>: TMoveBase<T> { using TMoveBase<T>::TMoveBase; constexpr TCopyAssignBase() noexcept = default; @@ -137,12 +137,12 @@ namespace NMaybe { // -------------------- MOVE ASSIGN -------------------- template <class T, bool = std::is_trivially_copy_assignable<T>::value> - struct TMoveAssignBase: TCopyAssignBase<T> { + struct TMoveAssignBase: TCopyAssignBase<T> { using TCopyAssignBase<T>::TCopyAssignBase; }; template <class T> - struct TMoveAssignBase<T, false>: TCopyAssignBase<T> { + struct TMoveAssignBase<T, false>: TCopyAssignBase<T> { using TCopyAssignBase<T>::TCopyAssignBase; constexpr TMoveAssignBase() noexcept = default; @@ -150,8 +150,8 @@ namespace NMaybe { constexpr TMoveAssignBase(TMoveAssignBase&&) = default; TMoveAssignBase& operator=(const TMoveAssignBase&) = default; TMoveAssignBase& operator=(TMoveAssignBase&& rhs) noexcept( - std::is_nothrow_move_assignable<T>::value&& - std::is_nothrow_move_constructible<T>::value) + std::is_nothrow_move_assignable<T>::value&& + std::is_nothrow_move_constructible<T>::value) { if (this->Defined_) { if (rhs.Defined_) { diff --git a/util/generic/maybe_ut.cpp b/util/generic/maybe_ut.cpp index 706ef25d85..2c1a425c5e 100644 --- a/util/generic/maybe_ut.cpp +++ b/util/generic/maybe_ut.cpp @@ -1,6 +1,6 @@ #include <util/generic/string.h> #include <util/generic/vector.h> -#include <util/stream/str.h> +#include <util/stream/str.h> #include <library/cpp/testing/unittest/registar.h> #include "maybe.h" @@ -40,19 +40,19 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { } Y_UNIT_TEST(TestWarning) { - TMaybe<size_t> x; - TStringStream ss; + TMaybe<size_t> x; + TStringStream ss; TString line; - - while (ss.ReadLine(line)) { - x = line.size(); - } - + + while (ss.ReadLine(line)) { + x = line.size(); + } + if (x == 5u) { - ss << "5\n"; - } - } - + ss << "5\n"; + } + } + Y_UNIT_TEST(TTestConstructorDestructor) { int a = 0; int b = 0; @@ -140,22 +140,22 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { m5 = {}; UNIT_ASSERT(m5.Empty()); } - + Y_UNIT_TEST(TestInPlace) { - TMaybe<int> m; - - UNIT_ASSERT(!m); - - m.ConstructInPlace(1); - - UNIT_ASSERT(m == 1); - + TMaybe<int> m; + + UNIT_ASSERT(!m); + + m.ConstructInPlace(1); + + UNIT_ASSERT(m == 1); + auto& x = m.ConstructInPlace(2); - - UNIT_ASSERT(m == 2); + + UNIT_ASSERT(m == 2); x = 7; UNIT_ASSERT(m == 7); - } + } Y_UNIT_TEST(TestMove) { struct TMovable { @@ -239,7 +239,7 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { } } - /* + /* == != < @@ -261,8 +261,8 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { } Y_UNIT_TEST(TestCompareEqualNonEmpty) { - TMaybe<int> m1{1}; - TMaybe<int> m2{1}; + TMaybe<int> m1{1}; + TMaybe<int> m2{1}; UNIT_ASSERT(m1 == m2); UNIT_ASSERT(!(m1 != m2)); @@ -273,8 +273,8 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { } Y_UNIT_TEST(TestCompareOneLessThanOther) { - TMaybe<int> m1{1}; - TMaybe<int> m2{2}; + TMaybe<int> m1{1}; + TMaybe<int> m2{2}; UNIT_ASSERT(!(m1 == m2)); UNIT_ASSERT(m1 != m2); @@ -285,8 +285,8 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { } Y_UNIT_TEST(TestCompareTMaybeAndT_Equal) { - TMaybe<int> m{1}; - int v{1}; + TMaybe<int> m{1}; + int v{1}; UNIT_ASSERT(m == v); UNIT_ASSERT(!(m != v)); @@ -304,8 +304,8 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { } Y_UNIT_TEST(TestCompareTMaybeAndT_TMaybeLessThanT) { - TMaybe<int> m{1}; - int v{2}; + TMaybe<int> m{1}; + int v{2}; UNIT_ASSERT(!(m == v)); UNIT_ASSERT(m != v); @@ -323,8 +323,8 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { } Y_UNIT_TEST(TestCompareTMaybeAndT_TMaybeGreaterThanT) { - TMaybe<int> m{2}; - int v{1}; + TMaybe<int> m{2}; + int v{1}; UNIT_ASSERT(!(m == v)); UNIT_ASSERT(m != v); @@ -343,7 +343,7 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { Y_UNIT_TEST(TestCompareEmptyTMaybeAndT) { TMaybe<int> m; - int v{1}; + int v{1}; UNIT_ASSERT(!(m == v)); UNIT_ASSERT(m != v); @@ -380,7 +380,7 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { } Y_UNIT_TEST(TestCompareNonEmptyTMaybeAndNothing) { - TMaybe<int> m{1}; + TMaybe<int> m{1}; auto n = Nothing(); UNIT_ASSERT(!(m == n)); @@ -399,8 +399,8 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { } Y_UNIT_TEST(TestCompareTMaybeAndConvertibleT_Equal) { - TMaybe<size_t> m{1}; - unsigned int v{1}; + TMaybe<size_t> m{1}; + unsigned int v{1}; UNIT_ASSERT(m == v); UNIT_ASSERT(!(m != v)); @@ -418,8 +418,8 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { } Y_UNIT_TEST(TestCompareTMaybeAndConvertibleT_TMaybeLessThanT) { - TMaybe<size_t> m{1}; - unsigned int v{2}; + TMaybe<size_t> m{1}; + unsigned int v{2}; UNIT_ASSERT(!(m == v)); UNIT_ASSERT(m != v); @@ -437,8 +437,8 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { } Y_UNIT_TEST(TestCompareTMaybeAndConvertibleT_TMaybeGreaterThanT) { - TMaybe<size_t> m{2}; - unsigned int v{1}; + TMaybe<size_t> m{2}; + unsigned int v{1}; UNIT_ASSERT(!(m == v)); UNIT_ASSERT(m != v); @@ -457,7 +457,7 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { Y_UNIT_TEST(TestCompareEmptyTMaybeAndConvertibleT) { TMaybe<size_t> m; - unsigned int v{1}; + unsigned int v{1}; UNIT_ASSERT(!(m == v)); UNIT_ASSERT(m != v); @@ -518,10 +518,10 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { } int I_; - bool IsCopyConstructorCalled_{false}; - bool IsMoveConstructorCalled_{false}; - bool IsCopyAssignmentOperatorCalled_{false}; - bool IsMoveAssignmentOperatorCalled_{false}; + bool IsCopyConstructorCalled_{false}; + bool IsMoveConstructorCalled_{false}; + bool IsCopyAssignmentOperatorCalled_{false}; + bool IsMoveAssignmentOperatorCalled_{false}; }; auto m2 = MakeMaybe<TMockClass>(1); @@ -574,7 +574,7 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { bool SomeFlag_; }; - auto m5 = MakeMaybe<TMockStruct5>({1, 2, 3}, true); + auto m5 = MakeMaybe<TMockStruct5>({1, 2, 3}, true); UNIT_ASSERT(m5->Vec_.size() == 3); UNIT_ASSERT(m5->Vec_[0] == 1); UNIT_ASSERT(m5->Vec_[1] == 2); @@ -813,8 +813,8 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { struct TestStruct { TestStruct(int value) : Value_(value) - { - } + { + } operator int() const { return Value_; @@ -839,8 +839,8 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { struct TestStruct { explicit TestStruct(int value) : Value_(value) - { - } + { + } int Value_; }; @@ -857,8 +857,8 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { struct TestStruct { explicit TestStruct(int value) : Value_(value) - { - } + { + } TestStruct& operator=(int value) { Value_ = value; return *this; @@ -890,13 +890,13 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { TestStruct(int value) : Value_(value) , From_(FromValue) - { - } + { + } TestStruct(TMaybe<int> value) : Value_(value.Defined() ? value.GetRef() : 0) , From_(FromMaybe) - { - } + { + } int Value_; int From_; }; @@ -927,13 +927,13 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { TestStruct(int value) : Value_(value) , From_(FromValue) - { - } + { + } TestStruct(TMaybe<int> value) : Value_(value.Defined() ? value.GetRef() : 0) , From_(FromMaybe) - { - } + { + } TestStruct& operator=(int value) { Value_ = value; From_ = FromValue; @@ -971,14 +971,14 @@ Y_UNIT_TEST_SUITE(TMaybeTest) { bool FromMaybeConstructorApplied; explicit TDst(TSrc) - : FromMaybeConstructorApplied(false) - { - } + : FromMaybeConstructorApplied(false) + { + } explicit TDst(TMaybe<TSrc>) - : FromMaybeConstructorApplied(true) - { - } + : FromMaybeConstructorApplied(true) + { + } TDst& operator=(TSrc) { FromMaybeConstructorApplied = false; diff --git a/util/generic/mem_copy.cpp b/util/generic/mem_copy.cpp index d56efacf3d..dd96c6fbcf 100644 --- a/util/generic/mem_copy.cpp +++ b/util/generic/mem_copy.cpp @@ -1 +1 @@ -#include "mem_copy.h" +#include "mem_copy.h" diff --git a/util/generic/mem_copy.h b/util/generic/mem_copy.h index 2e97d265e9..b68c852953 100644 --- a/util/generic/mem_copy.h +++ b/util/generic/mem_copy.h @@ -1,55 +1,55 @@ -#pragma once - -#include "typetraits.h" - -#include <util/system/types.h> - -#include <cstring> - -template <class T> +#pragma once + +#include "typetraits.h" + +#include <util/system/types.h> + +#include <cstring> + +template <class T> using TIfPOD = std::enable_if_t<TTypeTraits<T>::IsPod, T*>; - -template <class T> + +template <class T> using TIfNotPOD = std::enable_if_t<!TTypeTraits<T>::IsPod, T*>; - -template <class T> + +template <class T> static inline TIfPOD<T> MemCopy(T* to, const T* from, size_t n) noexcept { - if (n) { - memcpy(to, from, n * sizeof(T)); - } - - return to; -} - -template <class T> -static inline TIfNotPOD<T> MemCopy(T* to, const T* from, size_t n) { - for (size_t i = 0; i < n; ++i) { - to[i] = from[i]; - } - - return to; -} - -template <class T> + if (n) { + memcpy(to, from, n * sizeof(T)); + } + + return to; +} + +template <class T> +static inline TIfNotPOD<T> MemCopy(T* to, const T* from, size_t n) { + for (size_t i = 0; i < n; ++i) { + to[i] = from[i]; + } + + return to; +} + +template <class T> static inline TIfPOD<T> MemMove(T* to, const T* from, size_t n) noexcept { - if (n) { - memmove(to, from, n * sizeof(T)); - } - - return to; -} - -template <class T> -static inline TIfNotPOD<T> MemMove(T* to, const T* from, size_t n) { - if (to <= from || to >= from + n) { - return MemCopy(to, from, n); - } - - //copy backwards - while (n) { - to[n - 1] = from[n - 1]; - --n; - } - - return to; -} + if (n) { + memmove(to, from, n * sizeof(T)); + } + + return to; +} + +template <class T> +static inline TIfNotPOD<T> MemMove(T* to, const T* from, size_t n) { + if (to <= from || to >= from + n) { + return MemCopy(to, from, n); + } + + //copy backwards + while (n) { + to[n - 1] = from[n - 1]; + --n; + } + + return to; +} diff --git a/util/generic/mem_copy_ut.cpp b/util/generic/mem_copy_ut.cpp index 59b6747655..8b55a11cf6 100644 --- a/util/generic/mem_copy_ut.cpp +++ b/util/generic/mem_copy_ut.cpp @@ -1,113 +1,113 @@ -#include "mem_copy.h" - +#include "mem_copy.h" + #include <library/cpp/testing/unittest/registar.h> - -namespace { + +namespace { class TAssignBCalled: public yexception { }; - struct TB { - inline TB& operator=(const TB&) { + struct TB { + inline TB& operator=(const TB&) { throw TAssignBCalled(); - - return *this; - } - }; - - struct TC: public TB { - }; -} - + + return *this; + } + }; + + struct TC: public TB { + }; +} + Y_DECLARE_PODTYPE(TB); - + Y_UNIT_TEST_SUITE(TestMemCopy) { Y_UNIT_TEST(Test1) { - char buf[] = "123"; - char buf1[sizeof(buf)]; - - UNIT_ASSERT_EQUAL(MemCopy(buf1, buf, sizeof(buf)), buf1); - - for (size_t i = 0; i < sizeof(buf); ++i) { - UNIT_ASSERT_VALUES_EQUAL(buf[i], buf1[i]); - } - } - - static int x = 0; - - struct TA { - inline TA() { - X = ++x; - } - - int X; - }; - + char buf[] = "123"; + char buf1[sizeof(buf)]; + + UNIT_ASSERT_EQUAL(MemCopy(buf1, buf, sizeof(buf)), buf1); + + for (size_t i = 0; i < sizeof(buf); ++i) { + UNIT_ASSERT_VALUES_EQUAL(buf[i], buf1[i]); + } + } + + static int x = 0; + + struct TA { + inline TA() { + X = ++x; + } + + int X; + }; + Y_UNIT_TEST(Test2) { - x = 0; - - TA a1[5]; - TA a2[5]; - - UNIT_ASSERT_VALUES_EQUAL(a1[0].X, 1); - UNIT_ASSERT_VALUES_EQUAL(a2[0].X, 6); - - MemCopy(a2, a1, 5); - - for (size_t i = 0; i < 5; ++i) { - UNIT_ASSERT_VALUES_EQUAL(a1[i].X, a2[i].X); - } - } - + x = 0; + + TA a1[5]; + TA a2[5]; + + UNIT_ASSERT_VALUES_EQUAL(a1[0].X, 1); + UNIT_ASSERT_VALUES_EQUAL(a2[0].X, 6); + + MemCopy(a2, a1, 5); + + for (size_t i = 0; i < 5; ++i) { + UNIT_ASSERT_VALUES_EQUAL(a1[i].X, a2[i].X); + } + } + Y_UNIT_TEST(Test3) { - TB b1[5]; - TB b2[5]; - - MemCopy(b2, b1, 5); - } - + TB b1[5]; + TB b2[5]; + + MemCopy(b2, b1, 5); + } + Y_UNIT_TEST(Test4) { - TC c1[5]; - TC c2[5]; - + TC c1[5]; + TC c2[5]; + UNIT_ASSERT_EXCEPTION(MemCopy(c2, c1, 5), TAssignBCalled); - } - - template <class T> - inline void FillX(T* b, T* e) { + } + + template <class T> + inline void FillX(T* b, T* e) { int tmp = 0; - - while (b != e) { + + while (b != e) { (b++)->X = ++tmp; - } - } - + } + } + Y_UNIT_TEST(Test5) { - struct TD { - int X; - }; - - TD orig[50]; - - for (ssize_t i = -15; i < 15; ++i) { - TD* b = orig + 20; - TD* e = b + 10; - - FillX(b, e); - - TD* to = b + i; - - MemMove(to, b, e - b - 1); - - for (size_t j = 0; j < (e - b) - (size_t)1; ++j) { - UNIT_ASSERT_VALUES_EQUAL(to[j].X, j + 1); - } - } - } - + struct TD { + int X; + }; + + TD orig[50]; + + for (ssize_t i = -15; i < 15; ++i) { + TD* b = orig + 20; + TD* e = b + 10; + + FillX(b, e); + + TD* to = b + i; + + MemMove(to, b, e - b - 1); + + for (size_t j = 0; j < (e - b) - (size_t)1; ++j) { + UNIT_ASSERT_VALUES_EQUAL(to[j].X, j + 1); + } + } + } + Y_UNIT_TEST(TestEmpty) { char* tmp = nullptr; - + UNIT_ASSERT(MemCopy(tmp, tmp, 0) == nullptr); UNIT_ASSERT(MemMove(tmp, tmp, 0) == nullptr); - } -} + } +} diff --git a/util/generic/noncopyable.cpp b/util/generic/noncopyable.cpp index 20c1f5c021..a614dca34f 100644 --- a/util/generic/noncopyable.cpp +++ b/util/generic/noncopyable.cpp @@ -1 +1 @@ -#include "noncopyable.h" +#include "noncopyable.h" diff --git a/util/generic/noncopyable.h b/util/generic/noncopyable.h index 1e9533b128..c007934133 100644 --- a/util/generic/noncopyable.h +++ b/util/generic/noncopyable.h @@ -4,7 +4,7 @@ * @class TNonCopyable * * Inherit your class from `TNonCopyable` if you want to make it noncopyable. - * + * * Example usage: * @code * class Foo: private TNonCopyable { @@ -13,11 +13,11 @@ * @endcode */ -namespace NNonCopyable { // protection from unintended ADL +namespace NNonCopyable { // protection from unintended ADL struct TNonCopyable { TNonCopyable(const TNonCopyable&) = delete; TNonCopyable& operator=(const TNonCopyable&) = delete; - + TNonCopyable() = default; ~TNonCopyable() = default; }; diff --git a/util/generic/object_counter.cpp b/util/generic/object_counter.cpp index 98e7026afc..09f4b272b5 100644 --- a/util/generic/object_counter.cpp +++ b/util/generic/object_counter.cpp @@ -1 +1 @@ -#include "object_counter.h" +#include "object_counter.h" diff --git a/util/generic/object_counter.h b/util/generic/object_counter.h index 87ea0c59f1..5257afa2e6 100644 --- a/util/generic/object_counter.h +++ b/util/generic/object_counter.h @@ -18,22 +18,22 @@ */ template <class T> class TObjectCounter { -public: +public: inline TObjectCounter() noexcept { - AtomicIncrement(Count_); - } + AtomicIncrement(Count_); + } inline TObjectCounter(const TObjectCounter& /*item*/) noexcept { AtomicIncrement(Count_); } inline ~TObjectCounter() { - AtomicDecrement(Count_); - } + AtomicDecrement(Count_); + } static inline long ObjectCount() noexcept { return AtomicGet(Count_); - } + } /** * Resets object count. Mainly for tests, as you don't want to do this in @@ -41,12 +41,12 @@ public: * * \returns Current object count. */ - static inline long ResetObjectCount() noexcept { + static inline long ResetObjectCount() noexcept { return AtomicSwap(&Count_, 0); - } + } -private: - static TAtomic Count_; +private: + static TAtomic Count_; }; template <class T> diff --git a/util/generic/overloaded.h b/util/generic/overloaded.h index 310a9af49e..96a97e44bc 100644 --- a/util/generic/overloaded.h +++ b/util/generic/overloaded.h @@ -1,7 +1,7 @@ #pragma once /** - * Construct an ad-hoc object with an overloaded `operator()`. + * Construct an ad-hoc object with an overloaded `operator()`. * * Typically used with lambdas to construct type-matching visitors for e.g. std::variant: * ``` @@ -48,7 +48,7 @@ */ template <class... Fs> -struct TOverloaded: Fs... { +struct TOverloaded: Fs... { using Fs::operator()...; }; diff --git a/util/generic/overloaded_ut.cpp b/util/generic/overloaded_ut.cpp index cb45a9143d..f3d73895ad 100644 --- a/util/generic/overloaded_ut.cpp +++ b/util/generic/overloaded_ut.cpp @@ -18,7 +18,7 @@ Y_UNIT_TEST_SUITE(TOverloadedTest) { auto f = TOverloaded{ [](const TType1&) {}, [](const TType2&) {}, - [](const TType3&) {}}; + [](const TType3&) {}}; using F = decltype(f); static_assert(std::is_invocable_v<F, TType1>); static_assert(std::is_invocable_v<F, TType2>); @@ -39,14 +39,14 @@ Y_UNIT_TEST_SUITE(TOverloadedTest) { } Y_UNIT_TEST(TupleTest) { - std::tuple<int, double, bool, int> t{5, 3.14, true, 20}; + std::tuple<int, double, bool, int> t{5, 3.14, true, 20}; TString res; ForEach(t, TOverloaded{ - [&](int val) { res += "(int) " + ToString(val) + ' '; }, - [&](double val) { res += "(double) " + ToString(val) + ' '; }, - [&](bool val) { res += "(bool) " + ToString(val) + ' '; }, - }); + [&](int val) { res += "(int) " + ToString(val) + ' '; }, + [&](double val) { res += "(double) " + ToString(val) + ' '; }, + [&](bool val) { res += "(bool) " + ToString(val) + ' '; }, + }); UNIT_ASSERT_VALUES_EQUAL(res, "(int) 5 (double) 3.14 (bool) 1 (int) 20 "); } diff --git a/util/generic/ptr.cpp b/util/generic/ptr.cpp index ab8e7ca192..b29baebc17 100644 --- a/util/generic/ptr.cpp +++ b/util/generic/ptr.cpp @@ -1,17 +1,17 @@ -#include "ptr.h" - -#include <util/system/defaults.h> -#include <util/memory/alloc.h> - -#include <new> -#include <cstdlib> - +#include "ptr.h" + +#include <util/system/defaults.h> +#include <util/memory/alloc.h> + +#include <new> +#include <cstdlib> + void TFree::DoDestroy(void* t) noexcept { free(t); -} - +} + void TDelete::Destroy(void* t) noexcept { ::operator delete(t); -} - +} + TThrRefBase::~TThrRefBase() = default; diff --git a/util/generic/ptr.h b/util/generic/ptr.h index e71cda285a..19db0e3ec5 100644 --- a/util/generic/ptr.h +++ b/util/generic/ptr.h @@ -1,22 +1,22 @@ #pragma once - + #include "fwd.h" #include "utility.h" #include "intrlist.h" #include "refcount.h" #include "typetraits.h" -#include "singleton.h" - +#include "singleton.h" + #include <utility> - -#include <util/system/yassert.h> -#include <util/system/defaults.h> - + +#include <util/system/yassert.h> +#include <util/system/defaults.h> + template <class T, class U> using TGuardConversion = typename std::enable_if_t<std::is_convertible<U*, T*>::value>; -template <class T> -inline void AssertTypeComplete() { +template <class T> +inline void AssertTypeComplete() { // If compiler triggers this error from destructor of your class with // smart pointer, then may be you should move the destructor definition // to the .cpp file, where type T have full definition. @@ -25,213 +25,213 @@ inline void AssertTypeComplete() { // undefined behavior (missing destructor call/corrupted memory manager). // 'sizeof' is used to trigger compile-time error. static_assert(sizeof(T) != 0, "Type must be complete"); -} - -template <class T> -inline void CheckedDelete(T* t) { - AssertTypeComplete<T>(); - +} + +template <class T> +inline void CheckedDelete(T* t) { + AssertTypeComplete<T>(); + delete t; } -template <class T> -inline void CheckedArrayDelete(T* t) { - AssertTypeComplete<T>(); - - delete[] t; +template <class T> +inline void CheckedArrayDelete(T* t) { + AssertTypeComplete<T>(); + + delete[] t; } class TNoAction { -public: - template <class T> +public: + template <class T> static inline void Destroy(T*) noexcept { - } + } }; -class TDelete { -public: - template <class T> +class TDelete { +public: + template <class T> static inline void Destroy(T* t) noexcept { - CheckedDelete(t); - } - - /* + CheckedDelete(t); + } + + /* * special handling for nullptr - call nothing */ static inline void Destroy(std::nullptr_t) noexcept { } /* - * special handling for void* - call ::operator delete() - */ + * special handling for void* - call ::operator delete() + */ static void Destroy(void* t) noexcept; -}; - -class TDeleteArray { -public: - template <class T> +}; + +class TDeleteArray { +public: + template <class T> static inline void Destroy(T* t) noexcept { - CheckedArrayDelete(t); - } -}; - -class TDestructor { -public: - template <class T> + CheckedArrayDelete(t); + } +}; + +class TDestructor { +public: + template <class T> static inline void Destroy(T* t) noexcept { - (void)t; - t->~T(); - } -}; - -class TFree { -public: - template <class T> + (void)t; + t->~T(); + } +}; + +class TFree { +public: + template <class T> static inline void Destroy(T* t) noexcept { - DoDestroy((void*)t); - } - -private: - /* - * we do not want dependancy on cstdlib here... - */ + DoDestroy((void*)t); + } + +private: + /* + * we do not want dependancy on cstdlib here... + */ static void DoDestroy(void* t) noexcept; -}; - -template <class Base, class T> -class TPointerCommon { -public: +}; + +template <class Base, class T> +class TPointerCommon { +public: using TValueType = T; inline T* operator->() const noexcept { T* ptr = AsT(); Y_ASSERT(ptr); return ptr; - } - -#ifndef __cpp_impl_three_way_comparison - template <class C> + } + +#ifndef __cpp_impl_three_way_comparison + template <class C> inline bool operator==(const C& p) const noexcept { - return (p == AsT()); - } - - template <class C> + return (p == AsT()); + } + + template <class C> inline bool operator!=(const C& p) const noexcept { - return (p != AsT()); - } -#endif - + return (p != AsT()); + } +#endif + inline explicit operator bool() const noexcept { return nullptr != AsT(); - } - -protected: + } + +protected: inline T* AsT() const noexcept { - return (static_cast<const Base*>(this))->Get(); - } - + return (static_cast<const Base*>(this))->Get(); + } + static inline T* DoRelease(T*& t) noexcept { - T* ret = t; + T* ret = t; t = nullptr; - return ret; - } -}; - -template <class Base, class T> -class TPointerBase: public TPointerCommon<Base, T> { -public: + return ret; + } +}; + +template <class Base, class T> +class TPointerBase: public TPointerCommon<Base, T> { +public: inline T& operator*() const noexcept { Y_ASSERT(this->AsT()); - - return *(this->AsT()); - } - + + return *(this->AsT()); + } + inline T& operator[](size_t n) const noexcept { Y_ASSERT(this->AsT()); - - return (this->AsT())[n]; - } -}; - -/* - * void*-like pointers does not have operator* - */ -template <class Base> -class TPointerBase<Base, void>: public TPointerCommon<Base, void> { -}; - + + return (this->AsT())[n]; + } +}; + +/* + * void*-like pointers does not have operator* + */ +template <class Base> +class TPointerBase<Base, void>: public TPointerCommon<Base, void> { +}; + template <class T, class D> -class TAutoPtr: public TPointerBase<TAutoPtr<T, D>, T> { -public: +class TAutoPtr: public TPointerBase<TAutoPtr<T, D>, T> { +public: inline TAutoPtr(T* t = nullptr) noexcept - : T_(t) - { - } - + : T_(t) + { + } + inline TAutoPtr(const TAutoPtr& t) noexcept - : T_(t.Release()) - { - } - + : T_(t.Release()) + { + } + inline ~TAutoPtr() { - DoDestroy(); - } - + DoDestroy(); + } + inline TAutoPtr& operator=(const TAutoPtr& t) noexcept { - if (this != &t) { - Reset(t.Release()); - } - - return *this; - } - + if (this != &t) { + Reset(t.Release()); + } + + return *this; + } + inline T* Release() const noexcept Y_WARN_UNUSED_RESULT { - return this->DoRelease(T_); - } - + return this->DoRelease(T_); + } + inline void Reset(T* t) noexcept { - if (T_ != t) { - DoDestroy(); - T_ = t; - } - } - + if (T_ != t) { + DoDestroy(); + T_ = t; + } + } + inline void Reset() noexcept { Destroy(); } inline void Destroy() noexcept { Reset(nullptr); - } - + } + inline void Swap(TAutoPtr& r) noexcept { - DoSwap(T_, r.T_); - } - + DoSwap(T_, r.T_); + } + inline T* Get() const noexcept { - return T_; - } - -#ifdef __cpp_impl_three_way_comparison + return T_; + } + +#ifdef __cpp_impl_three_way_comparison template <class Other> inline bool operator==(const Other& p) const noexcept { return (p == Get()); } -#endif -private: +#endif +private: inline void DoDestroy() noexcept { - if (T_) { - D::Destroy(T_); - } - } - -private: - mutable T* T_; -}; - + if (T_) { + D::Destroy(T_); + } + } + +private: + mutable T* T_; +}; + template <class T, class D> -class THolder: public TPointerBase<THolder<T, D>, T> { -public: +class THolder: public TPointerBase<THolder<T, D>, T> { +public: constexpr THolder() noexcept : T_(nullptr) { @@ -243,183 +243,183 @@ public: } explicit THolder(T* t) noexcept - : T_(t) - { - } - + : T_(t) + { + } + inline THolder(TAutoPtr<T, D> t) noexcept - : T_(t.Release()) - { - } - + : T_(t.Release()) + { + } + template <class U, class = TGuardConversion<T, U>> inline THolder(TAutoPtr<U, D> t) noexcept : T_(t.Release()) { } - inline THolder(THolder&& that) noexcept - : T_(that.Release()) - { - } + inline THolder(THolder&& that) noexcept + : T_(that.Release()) + { + } template <class U, class = TGuardConversion<T, U>> - inline THolder(THolder<U, D>&& that) noexcept - : T_(that.Release()) - { - } + inline THolder(THolder<U, D>&& that) noexcept + : T_(that.Release()) + { + } THolder(const THolder&) = delete; THolder& operator=(const THolder&) = delete; inline ~THolder() { - DoDestroy(); - } - + DoDestroy(); + } + inline void Destroy() noexcept { Reset(nullptr); - } - + } + inline T* Release() noexcept Y_WARN_UNUSED_RESULT { - return this->DoRelease(T_); - } - + return this->DoRelease(T_); + } + inline void Reset(T* t) noexcept { - if (T_ != t) { - DoDestroy(); - T_ = t; - } - } - + if (T_ != t) { + DoDestroy(); + T_ = t; + } + } + inline void Reset(TAutoPtr<T, D> t) noexcept { - Reset(t.Release()); - } + Reset(t.Release()); + } inline void Reset() noexcept { Destroy(); } inline void Swap(THolder& r) noexcept { - DoSwap(T_, r.T_); - } - + DoSwap(T_, r.T_); + } + inline T* Get() const noexcept { - return T_; - } - + return T_; + } + inline operator TAutoPtr<T, D>() noexcept { - return Release(); - } - + return Release(); + } + THolder& operator=(std::nullptr_t) noexcept { this->Reset(nullptr); return *this; } - THolder& operator=(THolder&& that) noexcept { - this->Reset(that.Release()); - return *this; - } + THolder& operator=(THolder&& that) noexcept { + this->Reset(that.Release()); + return *this; + } - template <class U> - THolder& operator=(THolder<U, D>&& that) noexcept { - this->Reset(that.Release()); - return *this; - } + template <class U> + THolder& operator=(THolder<U, D>&& that) noexcept { + this->Reset(that.Release()); + return *this; + } -#ifdef __cpp_impl_three_way_comparison +#ifdef __cpp_impl_three_way_comparison template <class Other> inline bool operator==(const Other& p) const noexcept { return (p == Get()); } -#endif -private: +#endif +private: inline void DoDestroy() noexcept { - if (T_) { - D::Destroy(T_); - } - } - -private: - T* T_; -}; - -template <typename T, typename... Args> + if (T_) { + D::Destroy(T_); + } + } + +private: + T* T_; +}; + +template <typename T, typename... Args> [[nodiscard]] THolder<T> MakeHolder(Args&&... args) { return THolder<T>(new T(std::forward<Args>(args)...)); } -/* - * usage: - * class T: public TRefCounted<T> - * and we get methods Ref() && UnRef() with - * proper destruction of last UnRef() - */ +/* + * usage: + * class T: public TRefCounted<T> + * and we get methods Ref() && UnRef() with + * proper destruction of last UnRef() + */ template <class T, class C, class D> -class TRefCounted { -public: +class TRefCounted { +public: inline TRefCounted(long initval = 0) noexcept - : Counter_(initval) - { - } - + : Counter_(initval) + { + } + inline ~TRefCounted() = default; - + inline void Ref(TAtomicBase d) noexcept { auto resultCount = Counter_.Add(d); Y_ASSERT(resultCount >= d); (void)resultCount; - } + } inline void Ref() noexcept { auto resultCount = Counter_.Inc(); Y_ASSERT(resultCount != 0); (void)resultCount; - } - + } + inline void UnRef(TAtomicBase d) noexcept { auto resultCount = Counter_.Sub(d); Y_ASSERT(resultCount >= 0); - if (resultCount == 0) { - D::Destroy(static_cast<T*>(this)); - } - } - + if (resultCount == 0) { + D::Destroy(static_cast<T*>(this)); + } + } + inline void UnRef() noexcept { - UnRef(1); - } + UnRef(1); + } inline TAtomicBase RefCount() const noexcept { - return Counter_.Val(); - } - + return Counter_.Val(); + } + inline void DecRef() noexcept { auto resultCount = Counter_.Dec(); Y_ASSERT(resultCount >= 0); (void)resultCount; - } + } - TRefCounted(const TRefCounted&) - : Counter_(0) - { - } + TRefCounted(const TRefCounted&) + : Counter_(0) + { + } - void operator=(const TRefCounted&) { - } + void operator=(const TRefCounted&) { + } + +private: + C Counter_; +}; -private: - C Counter_; -}; - /** * Atomically reference-counted base with a virtual destructor. * * @note Plays well with inheritance, should be used for refcounted base classes. */ -struct TThrRefBase: public TRefCounted<TThrRefBase, TAtomicCounter> { - virtual ~TThrRefBase(); -}; - +struct TThrRefBase: public TRefCounted<TThrRefBase, TAtomicCounter> { + virtual ~TThrRefBase(); +}; + /** * Atomically reference-counted base. * @@ -433,81 +433,81 @@ struct TThrRefBase: public TRefCounted<TThrRefBase, TAtomicCounter> { * @note To avoid accidental inheritance when it is not originally intended, * class @p T should be marked as final. */ -template <class T, class D = TDelete> -using TAtomicRefCount = TRefCounted<T, TAtomicCounter, D>; - +template <class T, class D = TDelete> +using TAtomicRefCount = TRefCounted<T, TAtomicCounter, D>; + /** * Non-atomically reference-counted base. * * @warning Not thread-safe. Use with great care. If in doubt, use @p ThrRefBase * or @p TAtomicRefCount instead. */ -template <class T, class D = TDelete> -using TSimpleRefCount = TRefCounted<T, TSimpleCounter, D>; - -template <class T> -class TDefaultIntrusivePtrOps { -public: +template <class T, class D = TDelete> +using TSimpleRefCount = TRefCounted<T, TSimpleCounter, D>; + +template <class T> +class TDefaultIntrusivePtrOps { +public: static inline void Ref(T* t) noexcept { Y_ASSERT(t); - - t->Ref(); - } - + + t->Ref(); + } + static inline void UnRef(T* t) noexcept { Y_ASSERT(t); - - t->UnRef(); - } + + t->UnRef(); + } static inline void DecRef(T* t) noexcept { Y_ASSERT(t); - t->DecRef(); - } - + t->DecRef(); + } + static inline long RefCount(const T* t) noexcept { Y_ASSERT(t); - - return t->RefCount(); - } -}; - + + return t->RefCount(); + } +}; + template <class T, class Ops> -class TIntrusivePtr: public TPointerBase<TIntrusivePtr<T, Ops>, T> { +class TIntrusivePtr: public TPointerBase<TIntrusivePtr<T, Ops>, T> { template <class U, class O> friend class TIntrusivePtr; - + template <class U, class O> friend class TIntrusiveConstPtr; -public: - struct TNoIncrement { - }; - +public: + struct TNoIncrement { + }; + inline TIntrusivePtr(T* t = nullptr) noexcept - : T_(t) - { - Ops(); - Ref(); - } - - inline TIntrusivePtr(T* t, TNoIncrement) noexcept - : T_(t) - { - Ops(); - } - + : T_(t) + { + Ops(); + Ref(); + } + + inline TIntrusivePtr(T* t, TNoIncrement) noexcept + : T_(t) + { + Ops(); + } + inline ~TIntrusivePtr() { UnRef(); - } - + } + inline TIntrusivePtr(const TIntrusivePtr& p) noexcept - : T_(p.T_) - { - Ref(); - } - + : T_(p.T_) + { + Ref(); + } + // NOTE: // without std::enable_if_t compiler sometimes tries to use this constructor inappropriately // e.g. @@ -531,18 +531,18 @@ public: p.T_ = nullptr; } - inline TIntrusivePtr(TIntrusivePtr&& p) noexcept - : T_(nullptr) - { - Swap(p); - } - + inline TIntrusivePtr(TIntrusivePtr&& p) noexcept + : T_(nullptr) + { + Swap(p); + } + inline TIntrusivePtr& operator=(TIntrusivePtr p) noexcept { - p.Swap(*this); - - return *this; - } - + p.Swap(*this); + + return *this; + } + // Effectively replace both: // Reset(const TIntrusivePtr&) // Reset(TIntrusivePtr&&) @@ -555,55 +555,55 @@ public: } inline T* Get() const noexcept { - return T_; - } - + return T_; + } + inline void Swap(TIntrusivePtr& r) noexcept { - DoSwap(T_, r.T_); - } - + DoSwap(T_, r.T_); + } + inline void Drop() noexcept { TIntrusivePtr(nullptr).Swap(*this); - } - + } + inline T* Release() const noexcept Y_WARN_UNUSED_RESULT { - T* res = T_; - if (T_) { - Ops::DecRef(T_); + T* res = T_; + if (T_) { + Ops::DecRef(T_); T_ = nullptr; } - return res; - } + return res; + } inline long RefCount() const noexcept { - return T_ ? Ops::RefCount(T_) : 0; - } - -#ifdef __cpp_impl_three_way_comparison + return T_ ? Ops::RefCount(T_) : 0; + } + +#ifdef __cpp_impl_three_way_comparison template <class Other> inline bool operator==(const Other& p) const noexcept { return (p == Get()); } -#endif -private: +#endif +private: inline void Ref() noexcept { - if (T_) { - Ops::Ref(T_); - } - } - + if (T_) { + Ops::Ref(T_); + } + } + inline void UnRef() noexcept { - if (T_) { - Ops::UnRef(T_); - } - } - -private: - mutable T* T_; -}; - + if (T_) { + Ops::UnRef(T_); + } + } + +private: + mutable T* T_; +}; + template <class T, class Ops> -struct THash<TIntrusivePtr<T, Ops>>: THash<const T*> { +struct THash<TIntrusivePtr<T, Ops>>: THash<const T*> { using THash<const T*>::operator(); inline size_t operator()(const TIntrusivePtr<T, Ops>& ptr) const { return THash<const T*>::operator()(ptr.Get()); @@ -613,35 +613,35 @@ struct THash<TIntrusivePtr<T, Ops>>: THash<const T*> { // Behaves like TIntrusivePtr but returns const T* to prevent user from accidentally modifying the referenced object. template <class T, class Ops> class TIntrusiveConstPtr: public TPointerBase<TIntrusiveConstPtr<T, Ops>, const T> { -public: +public: inline TIntrusiveConstPtr(T* t = nullptr) noexcept // we need a non-const pointer to Ref(), UnRef() and eventually delete it. - : T_(t) - { - Ops(); - Ref(); - } + : T_(t) + { + Ops(); + Ref(); + } inline ~TIntrusiveConstPtr() { - UnRef(); - } + UnRef(); + } inline TIntrusiveConstPtr(const TIntrusiveConstPtr& p) noexcept - : T_(p.T_) - { - Ref(); - } - - inline TIntrusiveConstPtr(TIntrusiveConstPtr&& p) noexcept - : T_(nullptr) - { - Swap(p); - } - + : T_(p.T_) + { + Ref(); + } + + inline TIntrusiveConstPtr(TIntrusiveConstPtr&& p) noexcept + : T_(nullptr) + { + Swap(p); + } + inline TIntrusiveConstPtr(TIntrusivePtr<T> p) noexcept : T_(p.T_) - { + { p.T_ = nullptr; - } + } template <class U, class = TGuardConversion<T, U>> inline TIntrusiveConstPtr(const TIntrusiveConstPtr<U>& p) noexcept @@ -658,10 +658,10 @@ public: } inline TIntrusiveConstPtr& operator=(TIntrusiveConstPtr p) noexcept { - p.Swap(*this); + p.Swap(*this); - return *this; - } + return *this; + } // Effectively replace both: // Reset(const TIntrusiveConstPtr&) @@ -675,49 +675,49 @@ public: } inline const T* Get() const noexcept { - return T_; - } + return T_; + } inline void Swap(TIntrusiveConstPtr& r) noexcept { - DoSwap(T_, r.T_); - } + DoSwap(T_, r.T_); + } inline void Drop() noexcept { TIntrusiveConstPtr(nullptr).Swap(*this); - } + } inline long RefCount() const noexcept { return T_ ? Ops::RefCount(T_) : 0; } -#ifdef __cpp_impl_three_way_comparison +#ifdef __cpp_impl_three_way_comparison template <class Other> inline bool operator==(const Other& p) const noexcept { return (p == Get()); } -#endif -private: +#endif +private: inline void Ref() noexcept { if (T_ != nullptr) { - Ops::Ref(T_); + Ops::Ref(T_); } - } + } inline void UnRef() noexcept { if (T_ != nullptr) { - Ops::UnRef(T_); + Ops::UnRef(T_); } - } + } -private: - T* T_; +private: + T* T_; template <class U, class O> friend class TIntrusiveConstPtr; }; -template <class T, class Ops> -struct THash<TIntrusiveConstPtr<T, Ops>>: THash<const T*> { +template <class T, class Ops> +struct THash<TIntrusiveConstPtr<T, Ops>>: THash<const T*> { using THash<const T*>::operator(); inline size_t operator()(const TIntrusiveConstPtr<T, Ops>& ptr) const { return THash<const T*>::operator()(ptr.Get()); @@ -725,59 +725,59 @@ struct THash<TIntrusiveConstPtr<T, Ops>>: THash<const T*> { }; template <class T, class Ops> -class TSimpleIntrusiveOps { - using TFunc = void (*)(T*) -#if __cplusplus >= 201703 - noexcept -#endif - ; - +class TSimpleIntrusiveOps { + using TFunc = void (*)(T*) +#if __cplusplus >= 201703 + noexcept +#endif + ; + static void DoRef(T* t) noexcept { - Ops::Ref(t); - } - + Ops::Ref(t); + } + static void DoUnRef(T* t) noexcept { - Ops::UnRef(t); - } - -public: + Ops::UnRef(t); + } + +public: inline TSimpleIntrusiveOps() noexcept { - InitStaticOps(); - } - + InitStaticOps(); + } + inline ~TSimpleIntrusiveOps() = default; - + static inline void Ref(T* t) noexcept { - Ref_(t); - } - + Ref_(t); + } + static inline void UnRef(T* t) noexcept { - UnRef_(t); - } - -private: + UnRef_(t); + } + +private: static inline void InitStaticOps() noexcept { - struct TInit { - inline TInit() noexcept { - Ref_ = DoRef; - UnRef_ = DoUnRef; - } - }; - - Singleton<TInit>(); - } - -private: - static TFunc Ref_; - static TFunc UnRef_; -}; - -template <class T, class Ops> + struct TInit { + inline TInit() noexcept { + Ref_ = DoRef; + UnRef_ = DoUnRef; + } + }; + + Singleton<TInit>(); + } + +private: + static TFunc Ref_; + static TFunc UnRef_; +}; + +template <class T, class Ops> typename TSimpleIntrusiveOps<T, Ops>::TFunc TSimpleIntrusiveOps<T, Ops>::Ref_ = nullptr; - -template <class T, class Ops> + +template <class T, class Ops> typename TSimpleIntrusiveOps<T, Ops>::TFunc TSimpleIntrusiveOps<T, Ops>::UnRef_ = nullptr; - + template <typename T, class Ops = TDefaultIntrusivePtrOps<T>, typename... Args> [[nodiscard]] TIntrusivePtr<T, Ops> MakeIntrusive(Args&&... args) { return new T{std::forward<Args>(args)...}; @@ -789,63 +789,63 @@ template <typename T, class Ops = TDefaultIntrusivePtrOps<T>, typename... Args> } template <class T, class C, class D> -class TSharedPtr: public TPointerBase<TSharedPtr<T, C, D>, T> { - template <class TT, class CC, class DD> - friend class TSharedPtr; +class TSharedPtr: public TPointerBase<TSharedPtr<T, C, D>, T> { + template <class TT, class CC, class DD> + friend class TSharedPtr; -public: +public: inline TSharedPtr() noexcept - : T_(nullptr) - , C_(nullptr) - { - } - - inline TSharedPtr(T* t) { - THolder<T, D> h(t); - - Init(h); - } - - inline TSharedPtr(TAutoPtr<T, D> t) { - Init(t); - } - + : T_(nullptr) + , C_(nullptr) + { + } + + inline TSharedPtr(T* t) { + THolder<T, D> h(t); + + Init(h); + } + + inline TSharedPtr(TAutoPtr<T, D> t) { + Init(t); + } + inline TSharedPtr(T* t, C* c) noexcept - : T_(t) - , C_(c) - { - } - + : T_(t) + , C_(c) + { + } + template <class TT, class = TGuardConversion<T, TT>> inline TSharedPtr(THolder<TT>&& t) { Init(t); } - inline ~TSharedPtr() { - UnRef(); - } - + inline ~TSharedPtr() { + UnRef(); + } + inline TSharedPtr(const TSharedPtr& t) noexcept - : T_(t.T_) - , C_(t.C_) - { - Ref(); - } - - inline TSharedPtr(TSharedPtr&& t) noexcept - : T_(nullptr) - , C_(nullptr) - { - Swap(t); - } - + : T_(t.T_) + , C_(t.C_) + { + Ref(); + } + + inline TSharedPtr(TSharedPtr&& t) noexcept + : T_(nullptr) + , C_(nullptr) + { + Swap(t); + } + template <class TT, class = TGuardConversion<T, TT>> inline TSharedPtr(const TSharedPtr<TT, C, D>& t) noexcept - : T_(t.T_) - , C_(t.C_) - { - Ref(); - } + : T_(t.T_) + , C_(t.C_) + { + Ref(); + } template <class TT, class = TGuardConversion<T, TT>> inline TSharedPtr(TSharedPtr<TT, C, D>&& t) noexcept @@ -857,83 +857,83 @@ public: } inline TSharedPtr& operator=(TSharedPtr t) noexcept { - t.Swap(*this); - - return *this; - } - + t.Swap(*this); + + return *this; + } + // Effectively replace both: // Reset(const TSharedPtr& t) // Reset(TSharedPtr&& t) inline void Reset(TSharedPtr t) noexcept { Swap(t); - } - + } + inline void Reset() noexcept { Drop(); } inline void Drop() noexcept { - TSharedPtr().Swap(*this); - } + TSharedPtr().Swap(*this); + } inline T* Get() const noexcept { - return T_; - } - + return T_; + } + inline C* ReferenceCounter() const noexcept { - return C_; - } - + return C_; + } + inline void Swap(TSharedPtr& r) noexcept { - DoSwap(T_, r.T_); - DoSwap(C_, r.C_); - } - + DoSwap(T_, r.T_); + DoSwap(C_, r.C_); + } + inline long RefCount() const noexcept { - return C_ ? C_->Val() : 0; - } - -#ifdef __cpp_impl_three_way_comparison + return C_ ? C_->Val() : 0; + } + +#ifdef __cpp_impl_three_way_comparison template <class Other> inline bool operator==(const Other& p) const noexcept { return (p == Get()); } -#endif -private: - template <class X> - inline void Init(X& t) { +#endif +private: + template <class X> + inline void Init(X& t) { C_ = !!t ? new C(1) : nullptr; - T_ = t.Release(); - } - + T_ = t.Release(); + } + inline void Ref() noexcept { - if (C_) { - C_->Inc(); - } - } - + if (C_) { + C_->Inc(); + } + } + inline void UnRef() noexcept { - if (C_ && !C_->Dec()) { - DoDestroy(); - } - } - + if (C_ && !C_->Dec()) { + DoDestroy(); + } + } + inline void DoDestroy() noexcept { - if (T_) { - D::Destroy(T_); - } - - delete C_; - } - -private: - T* T_; - C* C_; -}; - + if (T_) { + D::Destroy(T_); + } + + delete C_; + } + +private: + T* T_; + C* C_; +}; + template <class T, class C, class D> -struct THash<TSharedPtr<T, C, D>>: THash<const T*> { +struct THash<TSharedPtr<T, C, D>>: THash<const T*> { using THash<const T*>::operator(); inline size_t operator()(const TSharedPtr<T, C, D>& ptr) const { return THash<const T*>::operator()(ptr.Get()); @@ -942,85 +942,85 @@ struct THash<TSharedPtr<T, C, D>>: THash<const T*> { template <class T, class D = TDelete> using TAtomicSharedPtr = TSharedPtr<T, TAtomicCounter, D>; - -// use with great care. if in doubt, use TAtomicSharedPtr instead + +// use with great care. if in doubt, use TAtomicSharedPtr instead template <class T, class D = TDelete> using TSimpleSharedPtr = TSharedPtr<T, TSimpleCounter, D>; - -template <typename T, typename C, typename... Args> + +template <typename T, typename C, typename... Args> [[nodiscard]] TSharedPtr<T, C> MakeShared(Args&&... args) { return new T{std::forward<Args>(args)...}; } -template <typename T, typename... Args> +template <typename T, typename... Args> [[nodiscard]] inline TAtomicSharedPtr<T> MakeAtomicShared(Args&&... args) { return MakeShared<T, TAtomicCounter>(std::forward<Args>(args)...); } -template <typename T, typename... Args> +template <typename T, typename... Args> [[nodiscard]] inline TSimpleSharedPtr<T> MakeSimpleShared(Args&&... args) { return MakeShared<T, TSimpleCounter>(std::forward<Args>(args)...); } class TCopyClone { -public: - template <class T> - static inline T* Copy(T* t) { - if (t) - return t->Clone(); +public: + template <class T> + static inline T* Copy(T* t) { + if (t) + return t->Clone(); return nullptr; - } + } }; class TCopyNew { -public: - template <class T> - static inline T* Copy(T* t) { - if (t) - return new T(*t); +public: + template <class T> + static inline T* Copy(T* t) { + if (t) + return new T(*t); return nullptr; - } + } }; template <class T, class C, class D> class TCopyPtr: public TPointerBase<TCopyPtr<T, C, D>, T> { -public: +public: inline TCopyPtr(T* t = nullptr) noexcept - : T_(t) - { - } - - inline TCopyPtr(const TCopyPtr& t) - : T_(C::Copy(t.Get())) - { - } - - inline TCopyPtr(TCopyPtr&& t) noexcept - : T_(nullptr) - { - Swap(t); - } - + : T_(t) + { + } + + inline TCopyPtr(const TCopyPtr& t) + : T_(C::Copy(t.Get())) + { + } + + inline TCopyPtr(TCopyPtr&& t) noexcept + : T_(nullptr) + { + Swap(t); + } + inline ~TCopyPtr() { - DoDestroy(); - } + DoDestroy(); + } inline TCopyPtr& operator=(TCopyPtr t) noexcept { - t.Swap(*this); + t.Swap(*this); - return *this; - } + return *this; + } inline T* Release() noexcept Y_WARN_UNUSED_RESULT { - return DoRelease(T_); - } + return DoRelease(T_); + } inline void Reset(T* t) noexcept { - if (T_ != t) { - DoDestroy(); - T_ = t; + if (T_ != t) { + DoDestroy(); + T_ = t; } - } + } inline void Reset() noexcept { Destroy(); @@ -1028,37 +1028,37 @@ public: inline void Destroy() noexcept { Reset(nullptr); - } + } inline void Swap(TCopyPtr& r) noexcept { - DoSwap(T_, r.T_); - } + DoSwap(T_, r.T_); + } inline T* Get() const noexcept { - return T_; - } + return T_; + } -#ifdef __cpp_impl_three_way_comparison +#ifdef __cpp_impl_three_way_comparison template <class Other> inline bool operator==(const Other& p) const noexcept { return (p == Get()); } -#endif -private: +#endif +private: inline void DoDestroy() noexcept { - if (T_) - D::Destroy(T_); - } + if (T_) + D::Destroy(T_); + } -private: - T* T_; +private: + T* T_; }; // Copy-on-write pointer template <class TPtr, class TCopy> class TCowPtr: public TPointerBase<TCowPtr<TPtr, TCopy>, const typename TPtr::TValueType> { using T = typename TPtr::TValueType; - + public: inline TCowPtr() = default; @@ -1102,12 +1102,12 @@ public: T_.Reset(); } -#ifdef __cpp_impl_three_way_comparison +#ifdef __cpp_impl_three_way_comparison template <class Other> inline bool operator==(const Other& p) const noexcept { return (p == Get()); } -#endif +#endif private: inline void Unshare() { if (Shared()) { @@ -1120,16 +1120,16 @@ private: }; // saves .Get() on argument passing. Intended usage: Func(TPtrArg<X> p); ... TIntrusivePtr<X> p2; Func(p2); -template <class T> -class TPtrArg { - T* Ptr; - +template <class T> +class TPtrArg { + T* Ptr; + public: - TPtrArg(T* p) + TPtrArg(T* p) : Ptr(p) { } - TPtrArg(const TIntrusivePtr<T>& p) + TPtrArg(const TIntrusivePtr<T>& p) : Ptr(p.Get()) { } diff --git a/util/generic/ptr_ut.cpp b/util/generic/ptr_ut.cpp index 7a457ae119..c2dcff23f6 100644 --- a/util/generic/ptr_ut.cpp +++ b/util/generic/ptr_ut.cpp @@ -1,165 +1,165 @@ -#include "ptr.h" -#include "vector.h" -#include "noncopyable.h" - +#include "ptr.h" +#include "vector.h" +#include "noncopyable.h" + #include <library/cpp/testing/unittest/registar.h> - + #include <util/generic/hash_set.h> #include <util/generic/is_in.h> #include <util/stream/output.h> -#include <util/system/thread.h> - -class TPointerTest: public TTestBase { - UNIT_TEST_SUITE(TPointerTest); - UNIT_TEST(TestTypedefs); - UNIT_TEST(TestSimpleIntrPtr); - UNIT_TEST(TestHolderPtr); - UNIT_TEST(TestHolderPtrMoveConstructor); - UNIT_TEST(TestHolderPtrMoveConstructorInheritance); - UNIT_TEST(TestHolderPtrMoveAssignment); - UNIT_TEST(TestHolderPtrMoveAssignmentInheritance); +#include <util/system/thread.h> + +class TPointerTest: public TTestBase { + UNIT_TEST_SUITE(TPointerTest); + UNIT_TEST(TestTypedefs); + UNIT_TEST(TestSimpleIntrPtr); + UNIT_TEST(TestHolderPtr); + UNIT_TEST(TestHolderPtrMoveConstructor); + UNIT_TEST(TestHolderPtrMoveConstructorInheritance); + UNIT_TEST(TestHolderPtrMoveAssignment); + UNIT_TEST(TestHolderPtrMoveAssignmentInheritance); UNIT_TEST(TestMakeHolder); - UNIT_TEST(TestTrulePtr); + UNIT_TEST(TestTrulePtr); UNIT_TEST(TestAutoToHolder); - UNIT_TEST(TestCopyPtr); - UNIT_TEST(TestIntrPtr); + UNIT_TEST(TestCopyPtr); + UNIT_TEST(TestIntrPtr); UNIT_TEST(TestIntrusiveConvertion); UNIT_TEST(TestIntrusiveConstConvertion); UNIT_TEST(TestIntrusiveConstConstruction); UNIT_TEST(TestMakeIntrusive); - UNIT_TEST(TestCopyOnWritePtr1); - UNIT_TEST(TestCopyOnWritePtr2); - UNIT_TEST(TestOperatorBool); + UNIT_TEST(TestCopyOnWritePtr1); + UNIT_TEST(TestCopyOnWritePtr2); + UNIT_TEST(TestOperatorBool); UNIT_TEST(TestMakeShared); UNIT_TEST(TestComparison); - UNIT_TEST(TestSimpleIntrusivePtrCtorTsan); + UNIT_TEST(TestSimpleIntrusivePtrCtorTsan); UNIT_TEST(TestRefCountedPtrsInHashSet) - UNIT_TEST_SUITE_END(); - -private: - void TestSimpleIntrusivePtrCtorTsan() { - struct S: public TAtomicRefCount<S> { - }; - + UNIT_TEST_SUITE_END(); + +private: + void TestSimpleIntrusivePtrCtorTsan() { + struct S: public TAtomicRefCount<S> { + }; + struct TLocalThread: public ISimpleThread { void* ThreadProc() override { - TSimpleIntrusivePtr<S> ptr; - return nullptr; - } - }; - - // Create TSimpleIntrusivePtr in different threads - // Its constructor should be thread-safe - - TLocalThread t1, t2; - - t1.Start(); - t2.Start(); - t1.Join(); - t2.Join(); - } - - inline void TestTypedefs() { - TAtomicSharedPtr<int>(new int(1)); - TSimpleSharedPtr<int>(new int(1)); - } - - void TestSimpleIntrPtr(); - void TestHolderPtr(); - void TestHolderPtrMoveConstructor(); - void TestHolderPtrMoveConstructorInheritance(); - void TestHolderPtrMoveAssignment(); - void TestHolderPtrMoveAssignmentInheritance(); + TSimpleIntrusivePtr<S> ptr; + return nullptr; + } + }; + + // Create TSimpleIntrusivePtr in different threads + // Its constructor should be thread-safe + + TLocalThread t1, t2; + + t1.Start(); + t2.Start(); + t1.Join(); + t2.Join(); + } + + inline void TestTypedefs() { + TAtomicSharedPtr<int>(new int(1)); + TSimpleSharedPtr<int>(new int(1)); + } + + void TestSimpleIntrPtr(); + void TestHolderPtr(); + void TestHolderPtrMoveConstructor(); + void TestHolderPtrMoveConstructorInheritance(); + void TestHolderPtrMoveAssignment(); + void TestHolderPtrMoveAssignmentInheritance(); void TestMakeHolder(); - void TestTrulePtr(); + void TestTrulePtr(); void TestAutoToHolder(); - void TestCopyPtr(); - void TestIntrPtr(); + void TestCopyPtr(); + void TestIntrPtr(); void TestIntrusiveConvertion(); void TestIntrusiveConstConvertion(); void TestIntrusiveConstConstruction(); void TestMakeIntrusive(); - void TestCopyOnWritePtr1(); - void TestCopyOnWritePtr2(); - void TestOperatorBool(); + void TestCopyOnWritePtr1(); + void TestCopyOnWritePtr2(); + void TestOperatorBool(); void TestMakeShared(); void TestComparison(); template <class T, class TRefCountedPtr> void TestRefCountedPtrsInHashSetImpl(); void TestRefCountedPtrsInHashSet(); -}; - -UNIT_TEST_SUITE_REGISTRATION(TPointerTest); - -static int cnt = 0; - -class A: public TAtomicRefCount<A> { -public: - inline A() { - ++cnt; - } - - inline A(const A&) - : TAtomicRefCount<A>(*this) - { - ++cnt; - } - - inline ~A() { - --cnt; - } -}; - +}; + +UNIT_TEST_SUITE_REGISTRATION(TPointerTest); + +static int cnt = 0; + +class A: public TAtomicRefCount<A> { +public: + inline A() { + ++cnt; + } + + inline A(const A&) + : TAtomicRefCount<A>(*this) + { + ++cnt; + } + + inline ~A() { + --cnt; + } +}; + static A* MakeA() { - return new A(); -} - -/* - * test compileability - */ -class B; + return new A(); +} + +/* + * test compileability + */ +class B; static TSimpleIntrusivePtr<B> GetB() { - throw 1; -} - + throw 1; +} + void Func() { TSimpleIntrusivePtr<B> b = GetB(); -} - -void TPointerTest::TestSimpleIntrPtr() { - { +} + +void TPointerTest::TestSimpleIntrPtr() { + { TSimpleIntrusivePtr<A> a1(MakeA()); TSimpleIntrusivePtr<A> a2(MakeA()); - TSimpleIntrusivePtr<A> a3 = a2; - - a1 = a2; - a2 = a3; - } - + TSimpleIntrusivePtr<A> a3 = a2; + + a1 = a2; + a2 = a3; + } + UNIT_ASSERT_VALUES_EQUAL(cnt, 0); -} - -void TPointerTest::TestHolderPtr() { - { +} + +void TPointerTest::TestHolderPtr() { + { THolder<A> a1(MakeA()); - THolder<A> a2(a1.Release()); - } - + THolder<A> a2(a1.Release()); + } + UNIT_ASSERT_VALUES_EQUAL(cnt, 0); -} - +} + THolder<int> CreateInt(int value) { THolder<int> res(new int); *res = value; return res; } -void TPointerTest::TestHolderPtrMoveConstructor() { +void TPointerTest::TestHolderPtrMoveConstructor() { THolder<int> h = CreateInt(42); UNIT_ASSERT_VALUES_EQUAL(*h, 42); } -void TPointerTest::TestHolderPtrMoveAssignment() { +void TPointerTest::TestHolderPtrMoveAssignment() { THolder<int> h(new int); h = CreateInt(42); UNIT_ASSERT_VALUES_EQUAL(*h, 42); @@ -169,21 +169,21 @@ struct TBase { virtual ~TBase() = default; }; -struct TDerived: public TBase { +struct TDerived: public TBase { }; -void TPointerTest::TestHolderPtrMoveConstructorInheritance() { +void TPointerTest::TestHolderPtrMoveConstructorInheritance() { // compileability test THolder<TBase> basePtr(THolder<TDerived>(new TDerived)); } -void TPointerTest::TestHolderPtrMoveAssignmentInheritance() { +void TPointerTest::TestHolderPtrMoveAssignmentInheritance() { // compileability test THolder<TBase> basePtr; basePtr = THolder<TDerived>(new TDerived); } -void TPointerTest::TestMakeHolder() { +void TPointerTest::TestMakeHolder() { { auto ptr = MakeHolder<int>(5); UNIT_ASSERT_VALUES_EQUAL(*ptr, 5); @@ -191,10 +191,10 @@ void TPointerTest::TestMakeHolder() { { struct TRec { int X, Y; - TRec() - : X(1) - , Y(2) - { + TRec() + : X(1) + , Y(2) + { } }; THolder<TRec> ptr = MakeHolder<TRec>(); @@ -207,8 +207,8 @@ void TPointerTest::TestMakeHolder() { TRec(int x, int y) : X(x) , Y(y) - { - } + { + } }; auto ptr = MakeHolder<TRec>(1, 2); UNIT_ASSERT_VALUES_EQUAL(ptr->X, 1); @@ -218,20 +218,20 @@ void TPointerTest::TestMakeHolder() { class TRec { private: int X_, Y_; - + public: - TRec(int x, int y) + TRec(int x, int y) : X_(x) , Y_(y) - { + { } - int GetX() const { + int GetX() const { return X_; - } - int GetY() const { + } + int GetY() const { return Y_; - } + } }; auto ptr = MakeHolder<TRec>(1, 2); UNIT_ASSERT_VALUES_EQUAL(ptr->GetX(), 1); @@ -239,17 +239,17 @@ void TPointerTest::TestMakeHolder() { } } -void TPointerTest::TestTrulePtr() { - { +void TPointerTest::TestTrulePtr() { + { TAutoPtr<A> a1(MakeA()); - TAutoPtr<A> a2(a1); - a1 = a2; - } - + TAutoPtr<A> a2(a1); + a1 = a2; + } + UNIT_ASSERT_VALUES_EQUAL(cnt, 0); -} +} -void TPointerTest::TestAutoToHolder() { +void TPointerTest::TestAutoToHolder() { { TAutoPtr<A> a1(MakeA()); THolder<A> a2(a1); @@ -278,7 +278,7 @@ void TPointerTest::TestAutoToHolder() { UNIT_ASSERT_VALUES_EQUAL(cnt, 0); } -void TPointerTest::TestCopyPtr() { +void TPointerTest::TestCopyPtr() { TCopyPtr<A> a1(MakeA()); { TCopyPtr<A> a2(MakeA()); @@ -294,25 +294,25 @@ void TPointerTest::TestCopyPtr() { UNIT_ASSERT_VALUES_EQUAL(cnt, 0); } -class TOp: public TSimpleRefCount<TOp>, public TNonCopyable { +class TOp: public TSimpleRefCount<TOp>, public TNonCopyable { public: static int Cnt; - + public: TOp() { ++Cnt; } - virtual ~TOp() { + virtual ~TOp() { --Cnt; } }; int TOp::Cnt = 0; -class TOp2: public TOp { +class TOp2: public TOp { public: TIntrusivePtr<TOp> Op; - + public: TOp2(const TIntrusivePtr<TOp>& op) : Op(op) @@ -335,7 +335,7 @@ void Attach(TOp3* op3, TIntrusivePtr<TOp>* op) { *op = op2.Get(); } -void TPointerTest::TestIntrPtr() { +void TPointerTest::TestIntrPtr() { { TIntrusivePtr<TOp> p, p2; TOp3 op3; @@ -365,11 +365,11 @@ void TPointerTest::TestIntrPtr() { } namespace NTestIntrusiveConvertion { - struct TA: public TSimpleRefCount<TA> { + struct TA: public TSimpleRefCount<TA> { }; - struct TAA: public TA { + struct TAA: public TA { }; - struct TB: public TSimpleRefCount<TB> { + struct TB: public TSimpleRefCount<TB> { }; void Func(TIntrusivePtr<TA>) { @@ -385,7 +385,7 @@ namespace NTestIntrusiveConvertion { } } -void TPointerTest::TestIntrusiveConvertion() { +void TPointerTest::TestIntrusiveConvertion() { using namespace NTestIntrusiveConvertion; TIntrusivePtr<TAA> aa = new TAA; @@ -401,7 +401,7 @@ void TPointerTest::TestIntrusiveConvertion() { Func(aa); } -void TPointerTest::TestIntrusiveConstConvertion() { +void TPointerTest::TestIntrusiveConstConvertion() { using namespace NTestIntrusiveConvertion; TIntrusiveConstPtr<TAA> aa = new TAA; @@ -417,7 +417,7 @@ void TPointerTest::TestIntrusiveConstConvertion() { Func(aa); } -void TPointerTest::TestMakeIntrusive() { +void TPointerTest::TestMakeIntrusive() { { UNIT_ASSERT_VALUES_EQUAL(0, TOp::Cnt); auto p = MakeIntrusive<TOp>(); @@ -427,7 +427,7 @@ void TPointerTest::TestMakeIntrusive() { UNIT_ASSERT_VALUES_EQUAL(TOp::Cnt, 0); } -void TPointerTest::TestCopyOnWritePtr1() { +void TPointerTest::TestCopyOnWritePtr1() { using TPtr = TCowPtr<TSimpleSharedPtr<int>>; TPtr p1; UNIT_ASSERT(!p1.Shared()); @@ -474,7 +474,7 @@ void TPointerTest::TestCopyOnWritePtr1() { UNIT_ASSERT_UNEQUAL(p2.Get(), p3.Get()); } -struct X: public TSimpleRefCount<X> { +struct X: public TSimpleRefCount<X> { inline X(int v = 0) : V(v) { @@ -483,7 +483,7 @@ struct X: public TSimpleRefCount<X> { int V; }; -void TPointerTest::TestCopyOnWritePtr2() { +void TPointerTest::TestCopyOnWritePtr2() { using TPtr = TCowPtr<TIntrusivePtr<X>>; TPtr p1; UNIT_ASSERT(!p1.Shared()); @@ -531,35 +531,35 @@ void TPointerTest::TestCopyOnWritePtr2() { } namespace { - template <class TFrom, class TTo> - struct TImplicitlyCastable { - struct RTYes { - char t[2]; - }; + template <class TFrom, class TTo> + struct TImplicitlyCastable { + struct RTYes { + char t[2]; + }; using RTNo = char; - static RTYes Func(TTo); - static RTNo Func(...); - static TFrom Get(); + static RTYes Func(TTo); + static RTNo Func(...); + static TFrom Get(); - /* + /* * Result == (TFrom could be converted to TTo implicitly) */ - enum { - Result = (sizeof(Func(Get())) != sizeof(RTNo)) - }; + enum { + Result = (sizeof(Func(Get())) != sizeof(RTNo)) + }; }; - struct TImplicitlyCastableToBool { - inline operator bool() const { - return true; - } - }; + struct TImplicitlyCastableToBool { + inline operator bool() const { + return true; + } + }; -} +} -void TPointerTest::TestOperatorBool() { +void TPointerTest::TestOperatorBool() { using TVec = TVector<ui32>; // to be sure TImplicitlyCastable works as expected @@ -573,9 +573,9 @@ void TPointerTest::TestOperatorBool() { UNIT_ASSERT(!(TImplicitlyCastable<TImplicitlyCastableToBool, void*>::Result)); // pointers - UNIT_ASSERT(!(TImplicitlyCastable<TSimpleSharedPtr<TVec>, int>::Result)); + UNIT_ASSERT(!(TImplicitlyCastable<TSimpleSharedPtr<TVec>, int>::Result)); UNIT_ASSERT(!(TImplicitlyCastable<TAutoPtr<ui64>, ui64>::Result)); - UNIT_ASSERT(!(TImplicitlyCastable<THolder<TVec>, bool>::Result)); // even this + UNIT_ASSERT(!(TImplicitlyCastable<THolder<TVec>, bool>::Result)); // even this { // mostly a compilability test @@ -583,45 +583,45 @@ void TPointerTest::TestOperatorBool() { THolder<TVec> a; UNIT_ASSERT(!a); UNIT_ASSERT(!bool(a)); - if (a) { + if (a) { UNIT_ASSERT(false); - } - if (!a) { + } + if (!a) { UNIT_ASSERT(true); - } + } a.Reset(new TVec); UNIT_ASSERT(a); UNIT_ASSERT(bool(a)); - if (a) { + if (a) { UNIT_ASSERT(true); - } - if (!a) { + } + if (!a) { UNIT_ASSERT(false); - } + } THolder<TVec> b(new TVec); UNIT_ASSERT(a.Get() != b.Get()); UNIT_ASSERT(a != b); - if (a == b) { + if (a == b) { UNIT_ASSERT(false); - } - if (a != b) { + } + if (a != b) { UNIT_ASSERT(true); - } - if (!(a && b)) { + } + if (!(a && b)) { UNIT_ASSERT(false); - } - if (a && b) { + } + if (a && b) { UNIT_ASSERT(true); - } + } // int i = a; // does not compile // bool c = (a < b); // does not compile } } -void TPointerTest::TestMakeShared() { +void TPointerTest::TestMakeShared() { { TSimpleSharedPtr<int> ptr = MakeSimpleShared<int>(5); UNIT_ASSERT_VALUES_EQUAL(*ptr, 5); @@ -629,10 +629,10 @@ void TPointerTest::TestMakeShared() { { struct TRec { int X, Y; - TRec() - : X(1) - , Y(2) - { + TRec() + : X(1) + , Y(2) + { } }; auto ptr = MakeAtomicShared<TRec>(); @@ -651,20 +651,20 @@ void TPointerTest::TestMakeShared() { class TRec { private: int X_, Y_; - + public: - TRec(int x, int y) + TRec(int x, int y) : X_(x) , Y_(y) - { + { } - int GetX() const { + int GetX() const { return X_; - } - int GetY() const { + } + int GetY() const { return Y_; - } + } }; TSimpleSharedPtr<TRec> ptr = MakeSimpleShared<TRec>(1, 2); UNIT_ASSERT_VALUES_EQUAL(ptr->GetX(), 1); @@ -718,7 +718,7 @@ void TestPtrComparison(const TPtr& ptr) { } void TPointerTest::TestComparison() { - THolder<A> ptr1(new A); + THolder<A> ptr1(new A); TAutoPtr<A> ptr2; TSimpleSharedPtr<int> ptr3(new int(6)); TIntrusivePtr<A> ptr4; @@ -754,13 +754,13 @@ void TPointerTest::TestRefCountedPtrsInHashSetImpl() { UNIT_ASSERT_VALUES_EQUAL(hashSet.size(), 2); } -struct TCustomIntrusivePtrOps: TDefaultIntrusivePtrOps<A> { +struct TCustomIntrusivePtrOps: TDefaultIntrusivePtrOps<A> { }; -struct TCustomDeleter: TDelete { +struct TCustomDeleter: TDelete { }; -struct TCustomCounter: TSimpleCounter { +struct TCustomCounter: TSimpleCounter { using TSimpleCounterTemplate::TSimpleCounterTemplate; }; diff --git a/util/generic/queue.cpp b/util/generic/queue.cpp index 52dd119921..4ebd3f3205 100644 --- a/util/generic/queue.cpp +++ b/util/generic/queue.cpp @@ -1 +1 @@ -#include "queue.h" +#include "queue.h" diff --git a/util/generic/queue.h b/util/generic/queue.h index 14348f6250..f5959f68f2 100644 --- a/util/generic/queue.h +++ b/util/generic/queue.h @@ -1,28 +1,28 @@ -#pragma once - +#pragma once + #include "fwd.h" -#include "deque.h" -#include "vector.h" -#include "utility.h" - -#include <util/str_stl.h> - -#include <queue> - +#include "deque.h" +#include "vector.h" +#include "utility.h" + +#include <util/str_stl.h> + +#include <queue> + template <class T, class S> class TQueue: public std::queue<T, S> { - using TBase = std::queue<T, S>; - -public: + using TBase = std::queue<T, S>; + +public: using TBase::TBase; - + inline explicit operator bool() const noexcept { return !this->empty(); } - inline void clear() { - this->c.clear(); - } + inline void clear() { + this->c.clear(); + } inline S& Container() { return this->c; @@ -31,23 +31,23 @@ public: inline const S& Container() const { return this->c; } -}; - +}; + template <class T, class S, class C> class TPriorityQueue: public std::priority_queue<T, S, C> { using TBase = std::priority_queue<T, S, C>; - -public: + +public: using TBase::TBase; - + inline explicit operator bool() const noexcept { return !this->empty(); } - inline void clear() { - this->c.clear(); - } - + inline void clear() { + this->c.clear(); + } + inline S& Container() { return this->c; } @@ -55,4 +55,4 @@ public: inline const S& Container() const { return this->c; } -}; +}; diff --git a/util/generic/queue_ut.cpp b/util/generic/queue_ut.cpp index b51bc607d4..a33399e104 100644 --- a/util/generic/queue_ut.cpp +++ b/util/generic/queue_ut.cpp @@ -1,9 +1,9 @@ -#include "queue.h" -#include "list.h" -#include "vector.h" - +#include "queue.h" +#include "list.h" +#include "vector.h" + #include <library/cpp/testing/unittest/registar.h> - + #include <utility> Y_UNIT_TEST_SUITE(TYQueueTest) { @@ -75,59 +75,59 @@ Y_UNIT_TEST_SUITE(TYQueueTest) { Y_UNIT_TEST(pqueue1) { TPriorityQueue<int, TDeque<int>, TLess<int>> q; - - q.push(42); - q.push(101); - q.push(69); - UNIT_ASSERT(q.top() == 101); - - q.pop(); - UNIT_ASSERT(q.top() == 69); - - q.pop(); - UNIT_ASSERT(q.top() == 42); - - q.pop(); - UNIT_ASSERT(q.empty()); - } - + + q.push(42); + q.push(101); + q.push(69); + UNIT_ASSERT(q.top() == 101); + + q.pop(); + UNIT_ASSERT(q.top() == 69); + + q.pop(); + UNIT_ASSERT(q.top() == 42); + + q.pop(); + UNIT_ASSERT(q.empty()); + } + Y_UNIT_TEST(pqueue2) { using TPQueue = TPriorityQueue<int, TDeque<int>, TLess<int>>; - TPQueue q; - - { - TPQueue qq; - - qq.push(42); - qq.push(101); - qq.push(69); - - qq.swap(q); - } - - UNIT_ASSERT(q.top() == 101); - - q.pop(); - UNIT_ASSERT(q.top() == 69); - - q.pop(); - UNIT_ASSERT(q.top() == 42); - - q.pop(); - UNIT_ASSERT(q.empty()); - } - + TPQueue q; + + { + TPQueue qq; + + qq.push(42); + qq.push(101); + qq.push(69); + + qq.swap(q); + } + + UNIT_ASSERT(q.top() == 101); + + q.pop(); + UNIT_ASSERT(q.top() == 69); + + q.pop(); + UNIT_ASSERT(q.top() == 42); + + q.pop(); + UNIT_ASSERT(q.empty()); + } + Y_UNIT_TEST(pqueue3) { TPriorityQueue<int, TDeque<int>, TLess<int>> q; - - q.push(42); - q.push(101); - q.push(69); - q.clear(); - - UNIT_ASSERT(q.empty()); - } - + + q.push(42); + q.push(101); + q.push(69); + q.clear(); + + UNIT_ASSERT(q.empty()); + } + Y_UNIT_TEST(pqueue4) { TDeque<int> c; c.push_back(42); @@ -154,57 +154,57 @@ Y_UNIT_TEST_SUITE(TYQueueTest) { Y_UNIT_TEST(queue1) { TQueue<int, TList<int>> q; - - q.push(42); - q.push(101); - q.push(69); - UNIT_ASSERT(q.front() == 42); - - q.pop(); - UNIT_ASSERT(q.front() == 101); - - q.pop(); - UNIT_ASSERT(q.front() == 69); - - q.pop(); - UNIT_ASSERT(q.empty()); - } - + + q.push(42); + q.push(101); + q.push(69); + UNIT_ASSERT(q.front() == 42); + + q.pop(); + UNIT_ASSERT(q.front() == 101); + + q.pop(); + UNIT_ASSERT(q.front() == 69); + + q.pop(); + UNIT_ASSERT(q.empty()); + } + Y_UNIT_TEST(queue2) { using TQueueType = TQueue<int>; TQueueType q; - - { + + { TQueueType qq; - - qq.push(42); - qq.push(101); - qq.push(69); - - qq.swap(q); - } - - UNIT_ASSERT(q.front() == 42); - - q.pop(); - UNIT_ASSERT(q.front() == 101); - - q.pop(); - UNIT_ASSERT(q.front() == 69); - - q.pop(); - UNIT_ASSERT(q.empty()); - } - + + qq.push(42); + qq.push(101); + qq.push(69); + + qq.swap(q); + } + + UNIT_ASSERT(q.front() == 42); + + q.pop(); + UNIT_ASSERT(q.front() == 101); + + q.pop(); + UNIT_ASSERT(q.front() == 69); + + q.pop(); + UNIT_ASSERT(q.empty()); + } + Y_UNIT_TEST(queue3) { using TQueueType = TQueue<int>; TQueueType q; - - q.push(42); - q.push(101); - q.push(69); - q.clear(); - - UNIT_ASSERT(q.empty()); - } -} + + q.push(42); + q.push(101); + q.push(69); + q.clear(); + + UNIT_ASSERT(q.empty()); + } +} diff --git a/util/generic/refcount.cpp b/util/generic/refcount.cpp index 08288beaa8..4174858ff9 100644 --- a/util/generic/refcount.cpp +++ b/util/generic/refcount.cpp @@ -1 +1 @@ -#include "refcount.h" +#include "refcount.h" diff --git a/util/generic/refcount.h b/util/generic/refcount.h index 7d53dc29d4..966e853b77 100644 --- a/util/generic/refcount.h +++ b/util/generic/refcount.h @@ -1,42 +1,42 @@ #pragma once - -#include <util/system/guard.h> -#include <util/system/atomic.h> + +#include <util/system/guard.h> +#include <util/system/atomic.h> #include <util/system/defaults.h> #include <util/system/yassert.h> - -template <class TCounterCheckPolicy> -class TSimpleCounterTemplate: public TCounterCheckPolicy { - using TCounterCheckPolicy::Check; -public: +template <class TCounterCheckPolicy> +class TSimpleCounterTemplate: public TCounterCheckPolicy { + using TCounterCheckPolicy::Check; + +public: inline TSimpleCounterTemplate(long initial = 0) noexcept - : Counter_(initial) - { - } - + : Counter_(initial) + { + } + inline ~TSimpleCounterTemplate() { - Check(); - } - + Check(); + } + inline TAtomicBase Add(TAtomicBase d) noexcept { - Check(); + Check(); return Counter_ += d; - } + } inline TAtomicBase Inc() noexcept { return Add(1); - } + } inline TAtomicBase Sub(TAtomicBase d) noexcept { - Check(); - return Counter_ -= d; - } - + Check(); + return Counter_ -= d; + } + inline TAtomicBase Dec() noexcept { - return Sub(1); - } - + return Sub(1); + } + inline bool TryWeakInc() noexcept { if (!Counter_) { return false; @@ -49,10 +49,10 @@ public: } inline TAtomicBase Val() const noexcept { - return Counter_; - } - -private: + return Counter_; + } + +private: TAtomicBase Counter_; }; @@ -64,7 +64,7 @@ protected: #if defined(SIMPLE_COUNTER_THREAD_CHECK) - #include <util/system/thread.i> + #include <util/system/thread.i> class TCheckPolicy { public: @@ -83,7 +83,7 @@ private: #else using TCheckPolicy = TNoCheckPolicy; #endif - + // Use this one if access from multiple threads to your pointer is an error and you want to enforce thread checks using TSimpleCounter = TSimpleCounterTemplate<TCheckPolicy>; // Use this one if you do want to share the pointer between threads, omit thread checks and do the synchronization yourself @@ -100,35 +100,35 @@ struct TCommonLockOps<TSimpleCounterTemplate<TCounterCheckPolicy>> { } }; -class TAtomicCounter { -public: +class TAtomicCounter { +public: inline TAtomicCounter(long initial = 0) noexcept - : Counter_(initial) - { - } - + : Counter_(initial) + { + } + inline ~TAtomicCounter() = default; - + inline TAtomicBase Add(TAtomicBase d) noexcept { return AtomicAdd(Counter_, d); - } + } inline TAtomicBase Inc() noexcept { return Add(1); - } - + } + inline TAtomicBase Sub(TAtomicBase d) noexcept { - return AtomicSub(Counter_, d); - } + return AtomicSub(Counter_, d); + } inline TAtomicBase Dec() noexcept { - return Sub(1); - } - + return Sub(1); + } + inline TAtomicBase Val() const noexcept { - return AtomicGet(Counter_); - } - + return AtomicGet(Counter_); + } + inline bool TryWeakInc() noexcept { while (true) { intptr_t curValue = Counter_; @@ -146,16 +146,16 @@ public: } } -private: - TAtomic Counter_; -}; - -template <> +private: + TAtomic Counter_; +}; + +template <> struct TCommonLockOps<TAtomicCounter> { static inline void Acquire(TAtomicCounter* t) noexcept { t->Inc(); } - + static inline void Release(TAtomicCounter* t) noexcept { t->Dec(); } diff --git a/util/generic/reserve.h b/util/generic/reserve.h index d859ebe850..81ceed19dc 100644 --- a/util/generic/reserve.h +++ b/util/generic/reserve.h @@ -7,5 +7,5 @@ namespace NDetail { } constexpr ::NDetail::TReserveTag Reserve(size_t capacity) { - return ::NDetail::TReserveTag{capacity}; + return ::NDetail::TReserveTag{capacity}; } diff --git a/util/generic/scope.h b/util/generic/scope.h index e03d86bcde..b2c33af61e 100644 --- a/util/generic/scope.h +++ b/util/generic/scope.h @@ -10,14 +10,14 @@ namespace NPrivate { class TScopeGuard { public: TScopeGuard(const F& function) - : Function_{function} - { - } + : Function_{function} + { + } TScopeGuard(F&& function) - : Function_{std::move(function)} - { - } + : Function_{std::move(function)} + { + } TScopeGuard(TScopeGuard&&) = default; TScopeGuard(const TScopeGuard&) = default; @@ -26,17 +26,17 @@ namespace NPrivate { Function_(); } - private: - F Function_; - }; - + private: + F Function_; + }; + struct TMakeGuardHelper { template <class F> - TScopeGuard<F> operator|(F&& function) const { + TScopeGuard<F> operator|(F&& function) const { return std::forward<F>(function); } - }; -} + }; +} // \brief `Y_SCOPE_EXIT(captures) { body };` // @@ -46,7 +46,7 @@ namespace NPrivate { // @note expects `body` to provide no-throw guarantee, otherwise whenever an exception // is thrown and leaves the outermost block of `body`, the function `std::terminate` is called. // @see http://drdobbs.com/184403758 for detailed motivation. -#define Y_SCOPE_EXIT(...) const auto Y_GENERATE_UNIQUE_ID(scopeGuard) Y_DECLARE_UNUSED = ::NPrivate::TMakeGuardHelper{} | [__VA_ARGS__]() mutable -> void +#define Y_SCOPE_EXIT(...) const auto Y_GENERATE_UNIQUE_ID(scopeGuard) Y_DECLARE_UNUSED = ::NPrivate::TMakeGuardHelper{} | [__VA_ARGS__]() mutable -> void // \brief `Y_DEFER { body };` // @@ -62,4 +62,4 @@ namespace NPrivate { // ... try handle `item` ... // ok = true; // \endcode -#define Y_DEFER Y_SCOPE_EXIT(&) +#define Y_DEFER Y_SCOPE_EXIT(&) diff --git a/util/generic/scope_ut.cpp b/util/generic/scope_ut.cpp index d8977d519b..bdb434d487 100644 --- a/util/generic/scope_ut.cpp +++ b/util/generic/scope_ut.cpp @@ -1,6 +1,6 @@ #include "scope.h" -#include <util/generic/ptr.h> +#include <util/generic/ptr.h> #include <library/cpp/testing/unittest/registar.h> Y_UNIT_TEST_SUITE(ScopeToolsTest) { @@ -21,7 +21,7 @@ Y_UNIT_TEST_SUITE(ScopeToolsTest) { } Y_UNIT_TEST(OnScopeExitMoveTest) { - THolder<int> i{new int{10}}; + THolder<int> i{new int{10}}; int p = 0; { @@ -32,16 +32,16 @@ Y_UNIT_TEST_SUITE(ScopeToolsTest) { UNIT_ASSERT_VALUES_EQUAL(20, p); } - - Y_UNIT_TEST(TestDefer) { - int i = 0; - - { - Y_DEFER { - i = 20; - }; - } - - UNIT_ASSERT_VALUES_EQUAL(i, 20); - } + + Y_UNIT_TEST(TestDefer) { + int i = 0; + + { + Y_DEFER { + i = 20; + }; + } + + UNIT_ASSERT_VALUES_EQUAL(i, 20); + } } diff --git a/util/generic/serialized_enum.h b/util/generic/serialized_enum.h index fb847701b0..79df2bac22 100644 --- a/util/generic/serialized_enum.h +++ b/util/generic/serialized_enum.h @@ -29,7 +29,7 @@ in your ya.make * @tparam EnumT enum type */ template <typename EnumT> -Y_CONST_FUNCTION constexpr size_t GetEnumItemsCount(); +Y_CONST_FUNCTION constexpr size_t GetEnumItemsCount(); namespace NEnumSerializationRuntime { namespace NDetail { @@ -89,7 +89,7 @@ namespace NEnumSerializationRuntime { * @tparam EnumT enum type */ template <typename EnumT> -Y_CONST_FUNCTION ::NEnumSerializationRuntime::TMappedDictView<EnumT, TString> GetEnumNames() { +Y_CONST_FUNCTION ::NEnumSerializationRuntime::TMappedDictView<EnumT, TString> GetEnumNames() { return ::NEnumSerializationRuntime::GetEnumNamesImpl<EnumT>(); } @@ -99,7 +99,7 @@ Y_CONST_FUNCTION ::NEnumSerializationRuntime::TMappedDictView<EnumT, TString> Ge * @tparam EnumT enum type */ template <typename EnumT> -Y_CONST_FUNCTION ::NEnumSerializationRuntime::TMappedArrayView<EnumT> GetEnumAllValues() { +Y_CONST_FUNCTION ::NEnumSerializationRuntime::TMappedArrayView<EnumT> GetEnumAllValues() { return ::NEnumSerializationRuntime::GetEnumAllValuesImpl<EnumT>(); } @@ -109,7 +109,7 @@ Y_CONST_FUNCTION ::NEnumSerializationRuntime::TMappedArrayView<EnumT> GetEnumAll * @tparam EnumT enum type */ template <typename EnumT> -Y_CONST_FUNCTION const TString& GetEnumAllNames() { +Y_CONST_FUNCTION const TString& GetEnumAllNames() { return ::NEnumSerializationRuntime::GetEnumAllNamesImpl<EnumT>(); } @@ -119,7 +119,7 @@ Y_CONST_FUNCTION const TString& GetEnumAllNames() { * @tparam EnumT enum type */ template <typename EnumT> -Y_CONST_FUNCTION const TVector<TString>& GetEnumAllCppNames() { +Y_CONST_FUNCTION const TVector<TString>& GetEnumAllCppNames() { return ::NEnumSerializationRuntime::GetEnumAllCppNamesImpl<EnumT>(); } @@ -247,7 +247,7 @@ namespace NEnumSerializationRuntime { return Ref.size(); } - Y_PURE_FUNCTION bool empty() const { + Y_PURE_FUNCTION bool empty() const { return Ref.empty(); } @@ -370,7 +370,7 @@ namespace NEnumSerializationRuntime { return Ref.size(); } - Y_PURE_FUNCTION bool empty() const { + Y_PURE_FUNCTION bool empty() const { return Ref.empty(); } diff --git a/util/generic/serialized_enum_ut.cpp b/util/generic/serialized_enum_ut.cpp index 5a2419aba5..3a94e1d471 100644 --- a/util/generic/serialized_enum_ut.cpp +++ b/util/generic/serialized_enum_ut.cpp @@ -31,24 +31,24 @@ Y_UNIT_TEST_SUITE(TestSerializedEnum) { }; UNIT_ASSERT(TRepresentationTypeList::THave<typename TSelectEnumRepresentationType<ERegular>::TType>::value); - enum class ESmall: unsigned char { + enum class ESmall: unsigned char { Six = 6, }; UNIT_ASSERT(TRepresentationTypeList::THave<typename TSelectEnumRepresentationType<ESmall>::TType>::value); - enum class EHugeUnsigned: ui64 { + enum class EHugeUnsigned: ui64 { Value = 0, }; UNIT_ASSERT(TRepresentationTypeList::THave<typename TSelectEnumRepresentationType<EHugeUnsigned>::TType>::value); - enum class EHugeSigned: i64 { + enum class EHugeSigned: i64 { Value = -2, }; UNIT_ASSERT(TRepresentationTypeList::THave<typename TSelectEnumRepresentationType<EHugeSigned>::TType>::value); } Y_UNIT_TEST(MappedArrayView) { - enum class ETestEnum: signed char { + enum class ETestEnum: signed char { Zero = 0, One = 1, Two = 2, @@ -78,7 +78,7 @@ Y_UNIT_TEST_SUITE(TestSerializedEnum) { } Y_UNIT_TEST(MappedDictView) { - enum class ETestEnum: unsigned short { + enum class ETestEnum: unsigned short { Zero = 0, One = 1, Two = 2, diff --git a/util/generic/set.cpp b/util/generic/set.cpp index 506937a165..aa2f9c58e1 100644 --- a/util/generic/set.cpp +++ b/util/generic/set.cpp @@ -1 +1 @@ -#include "set.h" +#include "set.h" diff --git a/util/generic/set.h b/util/generic/set.h index d7c6afb826..4c437ca26f 100644 --- a/util/generic/set.h +++ b/util/generic/set.h @@ -1,20 +1,20 @@ #pragma once - + #include "fwd.h" #include <util/str_stl.h> -#include <util/memory/alloc.h> - +#include <util/memory/alloc.h> + #include <initializer_list> #include <memory> -#include <set> - +#include <set> + template <class K, class L, class A> class TSet: public std::set<K, L, TReboundAllocator<A, K>> { public: using TBase = std::set<K, L, TReboundAllocator<A, K>>; using TBase::TBase; - + inline explicit operator bool() const noexcept { return !this->empty(); } @@ -23,14 +23,14 @@ public: inline bool contains(const TheKey& key) const { return this->find(key) != this->end(); } -}; - +}; + template <class K, class L, class A> class TMultiSet: public std::multiset<K, L, TReboundAllocator<A, K>> { public: using TBase = std::multiset<K, L, TReboundAllocator<A, K>>; using TBase::TBase; - + inline explicit operator bool() const noexcept { return !this->empty(); } @@ -39,4 +39,4 @@ public: inline bool contains(const TheKey& key) const { return this->find(key) != this->end(); } -}; +}; diff --git a/util/generic/set_ut.cpp b/util/generic/set_ut.cpp index 36726933ca..d2769d327f 100644 --- a/util/generic/set_ut.cpp +++ b/util/generic/set_ut.cpp @@ -1,96 +1,96 @@ -#include "set.h" - +#include "set.h" + #include <library/cpp/testing/unittest/registar.h> - + #include <utility> - -#include <algorithm> - + +#include <algorithm> + Y_UNIT_TEST_SUITE(YSetTest) { Y_UNIT_TEST(TestSet1) { TSet<int, TLess<int>> s; - UNIT_ASSERT(!s); - UNIT_ASSERT(s.count(42) == 0); - s.insert(42); - UNIT_ASSERT(s); - UNIT_ASSERT(s.count(42) == 1); - s.insert(42); - UNIT_ASSERT(s.count(42) == 1); - size_t count = s.erase(42); - UNIT_ASSERT(count == 1); - } - + UNIT_ASSERT(!s); + UNIT_ASSERT(s.count(42) == 0); + s.insert(42); + UNIT_ASSERT(s); + UNIT_ASSERT(s.count(42) == 1); + s.insert(42); + UNIT_ASSERT(s.count(42) == 1); + size_t count = s.erase(42); + UNIT_ASSERT(count == 1); + } + Y_UNIT_TEST(TestSet2) { using int_set = TSet<int, TLess<int>>; - int_set s; + int_set s; std::pair<int_set::iterator, bool> p = s.insert(42); - UNIT_ASSERT(p.second == true); - p = s.insert(42); - UNIT_ASSERT(p.second == false); - - int array1[] = {1, 3, 6, 7}; - s.insert(array1, array1 + 4); - UNIT_ASSERT(distance(s.begin(), s.end()) == 5); - - int_set s2; - s2.swap(s); - UNIT_ASSERT(distance(s2.begin(), s2.end()) == 5); - UNIT_ASSERT(distance(s.begin(), s.end()) == 0); - - int_set s3; - s3.swap(s); - s3.swap(s2); - UNIT_ASSERT(distance(s.begin(), s.end()) == 0); - UNIT_ASSERT(distance(s2.begin(), s2.end()) == 0); - UNIT_ASSERT(distance(s3.begin(), s3.end()) == 5); - } - + UNIT_ASSERT(p.second == true); + p = s.insert(42); + UNIT_ASSERT(p.second == false); + + int array1[] = {1, 3, 6, 7}; + s.insert(array1, array1 + 4); + UNIT_ASSERT(distance(s.begin(), s.end()) == 5); + + int_set s2; + s2.swap(s); + UNIT_ASSERT(distance(s2.begin(), s2.end()) == 5); + UNIT_ASSERT(distance(s.begin(), s.end()) == 0); + + int_set s3; + s3.swap(s); + s3.swap(s2); + UNIT_ASSERT(distance(s.begin(), s.end()) == 0); + UNIT_ASSERT(distance(s2.begin(), s2.end()) == 0); + UNIT_ASSERT(distance(s3.begin(), s3.end()) == 5); + } + Y_UNIT_TEST(TestErase) { TSet<int, TLess<int>> s; - s.insert(1); - s.erase(s.begin()); - UNIT_ASSERT(s.empty()); - - size_t nb = s.erase(1); - UNIT_ASSERT(nb == 0); - } - + s.insert(1); + s.erase(s.begin()); + UNIT_ASSERT(s.empty()); + + size_t nb = s.erase(1); + UNIT_ASSERT(nb == 0); + } + Y_UNIT_TEST(TestInsert) { TSet<int> s; TSet<int>::iterator i = s.insert(s.end(), 0); - UNIT_ASSERT(*i == 0); - } - + UNIT_ASSERT(*i == 0); + } + Y_UNIT_TEST(TestFind) { TSet<int> s; - - UNIT_ASSERT(s.find(0) == s.end()); - + + UNIT_ASSERT(s.find(0) == s.end()); + TSet<int> const& crs = s; - - UNIT_ASSERT(crs.find(0) == crs.end()); - } - + + UNIT_ASSERT(crs.find(0) == crs.end()); + } + Y_UNIT_TEST(TestHas) { TSet<int> s; UNIT_ASSERT(!s.contains(0)); - + TSet<int> const& crs = s; UNIT_ASSERT(!crs.contains(0)); - s.insert(1); - s.insert(42); - s.insert(100); - s.insert(2); + s.insert(1); + s.insert(42); + s.insert(100); + s.insert(2); UNIT_ASSERT(s.contains(1)); UNIT_ASSERT(s.contains(2)); UNIT_ASSERT(s.contains(42)); UNIT_ASSERT(s.contains(100)); - } + } Y_UNIT_TEST(TestBounds) { - int array1[] = {1, 3, 6, 7}; + int array1[] = {1, 3, 6, 7}; TSet<int> s(array1, array1 + sizeof(array1) / sizeof(array1[0])); TSet<int> const& crs = s; @@ -98,311 +98,311 @@ Y_UNIT_TEST_SUITE(YSetTest) { TSet<int>::const_iterator scit; std::pair<TSet<int>::iterator, TSet<int>::iterator> pit; std::pair<TSet<int>::const_iterator, TSet<int>::const_iterator> pcit; - - //Check iterator on mutable set - sit = s.lower_bound(2); - UNIT_ASSERT(sit != s.end()); - UNIT_ASSERT(*sit == 3); - - sit = s.upper_bound(5); - UNIT_ASSERT(sit != s.end()); - UNIT_ASSERT(*sit == 6); - - pit = s.equal_range(6); - UNIT_ASSERT(pit.first != pit.second); - UNIT_ASSERT(pit.first != s.end()); - UNIT_ASSERT(*pit.first == 6); - UNIT_ASSERT(pit.second != s.end()); - UNIT_ASSERT(*pit.second == 7); - - pit = s.equal_range(4); - UNIT_ASSERT(pit.first == pit.second); - UNIT_ASSERT(pit.first != s.end()); - UNIT_ASSERT(*pit.first == 6); - UNIT_ASSERT(pit.second != s.end()); - UNIT_ASSERT(*pit.second == 6); - - //Check const_iterator on mutable set - scit = s.lower_bound(2); - UNIT_ASSERT(scit != s.end()); - UNIT_ASSERT(*scit == 3); - - scit = s.upper_bound(5); - UNIT_ASSERT(scit != s.end()); - UNIT_ASSERT(*scit == 6); - - pcit = s.equal_range(6); - UNIT_ASSERT(pcit.first != pcit.second); - UNIT_ASSERT(pcit.first != s.end()); - UNIT_ASSERT(*pcit.first == 6); - UNIT_ASSERT(pcit.second != s.end()); - UNIT_ASSERT(*pcit.second == 7); - - //Check const_iterator on const set - scit = crs.lower_bound(2); - UNIT_ASSERT(scit != crs.end()); - UNIT_ASSERT(*scit == 3); - - scit = crs.upper_bound(5); - UNIT_ASSERT(scit != crs.end()); - UNIT_ASSERT(*scit == 6); - - pcit = crs.equal_range(6); - UNIT_ASSERT(pcit.first != pcit.second); - UNIT_ASSERT(pcit.first != crs.end()); - UNIT_ASSERT(*pcit.first == 6); - UNIT_ASSERT(pcit.second != crs.end()); - UNIT_ASSERT(*pcit.second == 7); - } - + + //Check iterator on mutable set + sit = s.lower_bound(2); + UNIT_ASSERT(sit != s.end()); + UNIT_ASSERT(*sit == 3); + + sit = s.upper_bound(5); + UNIT_ASSERT(sit != s.end()); + UNIT_ASSERT(*sit == 6); + + pit = s.equal_range(6); + UNIT_ASSERT(pit.first != pit.second); + UNIT_ASSERT(pit.first != s.end()); + UNIT_ASSERT(*pit.first == 6); + UNIT_ASSERT(pit.second != s.end()); + UNIT_ASSERT(*pit.second == 7); + + pit = s.equal_range(4); + UNIT_ASSERT(pit.first == pit.second); + UNIT_ASSERT(pit.first != s.end()); + UNIT_ASSERT(*pit.first == 6); + UNIT_ASSERT(pit.second != s.end()); + UNIT_ASSERT(*pit.second == 6); + + //Check const_iterator on mutable set + scit = s.lower_bound(2); + UNIT_ASSERT(scit != s.end()); + UNIT_ASSERT(*scit == 3); + + scit = s.upper_bound(5); + UNIT_ASSERT(scit != s.end()); + UNIT_ASSERT(*scit == 6); + + pcit = s.equal_range(6); + UNIT_ASSERT(pcit.first != pcit.second); + UNIT_ASSERT(pcit.first != s.end()); + UNIT_ASSERT(*pcit.first == 6); + UNIT_ASSERT(pcit.second != s.end()); + UNIT_ASSERT(*pcit.second == 7); + + //Check const_iterator on const set + scit = crs.lower_bound(2); + UNIT_ASSERT(scit != crs.end()); + UNIT_ASSERT(*scit == 3); + + scit = crs.upper_bound(5); + UNIT_ASSERT(scit != crs.end()); + UNIT_ASSERT(*scit == 6); + + pcit = crs.equal_range(6); + UNIT_ASSERT(pcit.first != pcit.second); + UNIT_ASSERT(pcit.first != crs.end()); + UNIT_ASSERT(*pcit.first == 6); + UNIT_ASSERT(pcit.second != crs.end()); + UNIT_ASSERT(*pcit.second == 7); + } + Y_UNIT_TEST(TestImplementationCheck) { TSet<int> tree; - tree.insert(1); + tree.insert(1); TSet<int>::iterator it = tree.begin(); - int const& int_ref = *it++; - UNIT_ASSERT(int_ref == 1); - - UNIT_ASSERT(it == tree.end()); - UNIT_ASSERT(it != tree.begin()); - + int const& int_ref = *it++; + UNIT_ASSERT(int_ref == 1); + + UNIT_ASSERT(it == tree.end()); + UNIT_ASSERT(it != tree.begin()); + TSet<int>::const_iterator cit = tree.begin(); - int const& int_cref = *cit++; - UNIT_ASSERT(int_cref == 1); - } - + int const& int_cref = *cit++; + UNIT_ASSERT(int_cref == 1); + } + Y_UNIT_TEST(TestReverseIteratorTest) { TSet<int> tree; - tree.insert(1); - tree.insert(2); - - { + tree.insert(1); + tree.insert(2); + + { TSet<int>::reverse_iterator rit(tree.rbegin()); - UNIT_ASSERT(*(rit++) == 2); - UNIT_ASSERT(*(rit++) == 1); - UNIT_ASSERT(rit == tree.rend()); - } - - { + UNIT_ASSERT(*(rit++) == 2); + UNIT_ASSERT(*(rit++) == 1); + UNIT_ASSERT(rit == tree.rend()); + } + + { TSet<int> const& ctree = tree; TSet<int>::const_reverse_iterator rit(ctree.rbegin()); - UNIT_ASSERT(*(rit++) == 2); - UNIT_ASSERT(*(rit++) == 1); - UNIT_ASSERT(rit == ctree.rend()); - } - } - + UNIT_ASSERT(*(rit++) == 2); + UNIT_ASSERT(*(rit++) == 1); + UNIT_ASSERT(rit == ctree.rend()); + } + } + Y_UNIT_TEST(TestConstructorsAndAssignments) { - { + { using container = TSet<int>; - - container c1; - c1.insert(100); - c1.insert(200); - container c2(c1); + container c1; + c1.insert(100); + c1.insert(200); - UNIT_ASSERT_VALUES_EQUAL(2, c1.size()); - UNIT_ASSERT_VALUES_EQUAL(2, c2.size()); + container c2(c1); + + UNIT_ASSERT_VALUES_EQUAL(2, c1.size()); + UNIT_ASSERT_VALUES_EQUAL(2, c2.size()); UNIT_ASSERT(c1.contains(100)); UNIT_ASSERT(c2.contains(200)); container c3(std::move(c1)); - UNIT_ASSERT_VALUES_EQUAL(0, c1.size()); - UNIT_ASSERT_VALUES_EQUAL(2, c3.size()); + UNIT_ASSERT_VALUES_EQUAL(0, c1.size()); + UNIT_ASSERT_VALUES_EQUAL(2, c3.size()); UNIT_ASSERT(c3.contains(100)); - c2.insert(300); - c3 = c2; + c2.insert(300); + c3 = c2; - UNIT_ASSERT_VALUES_EQUAL(3, c2.size()); - UNIT_ASSERT_VALUES_EQUAL(3, c3.size()); + UNIT_ASSERT_VALUES_EQUAL(3, c2.size()); + UNIT_ASSERT_VALUES_EQUAL(3, c3.size()); UNIT_ASSERT(c3.contains(300)); - c2.insert(400); + c2.insert(400); c3 = std::move(c2); - UNIT_ASSERT_VALUES_EQUAL(0, c2.size()); - UNIT_ASSERT_VALUES_EQUAL(4, c3.size()); + UNIT_ASSERT_VALUES_EQUAL(0, c2.size()); + UNIT_ASSERT_VALUES_EQUAL(4, c3.size()); UNIT_ASSERT(c3.contains(400)); - } + } - { + { using container = TMultiSet<int>; - container c1; - c1.insert(100); - c1.insert(200); + container c1; + c1.insert(100); + c1.insert(200); - container c2(c1); + container c2(c1); - UNIT_ASSERT_VALUES_EQUAL(2, c1.size()); - UNIT_ASSERT_VALUES_EQUAL(2, c2.size()); - UNIT_ASSERT(c1.find(100) != c1.end()); - UNIT_ASSERT(c2.find(200) != c2.end()); + UNIT_ASSERT_VALUES_EQUAL(2, c1.size()); + UNIT_ASSERT_VALUES_EQUAL(2, c2.size()); + UNIT_ASSERT(c1.find(100) != c1.end()); + UNIT_ASSERT(c2.find(200) != c2.end()); container c3(std::move(c1)); - UNIT_ASSERT_VALUES_EQUAL(0, c1.size()); - UNIT_ASSERT_VALUES_EQUAL(2, c3.size()); - UNIT_ASSERT(c3.find(100) != c3.end()); + UNIT_ASSERT_VALUES_EQUAL(0, c1.size()); + UNIT_ASSERT_VALUES_EQUAL(2, c3.size()); + UNIT_ASSERT(c3.find(100) != c3.end()); - c2.insert(300); - c3 = c2; + c2.insert(300); + c3 = c2; - UNIT_ASSERT_VALUES_EQUAL(3, c2.size()); - UNIT_ASSERT_VALUES_EQUAL(3, c3.size()); - UNIT_ASSERT(c3.find(300) != c3.end()); + UNIT_ASSERT_VALUES_EQUAL(3, c2.size()); + UNIT_ASSERT_VALUES_EQUAL(3, c3.size()); + UNIT_ASSERT(c3.find(300) != c3.end()); - c2.insert(400); + c2.insert(400); c3 = std::move(c2); - UNIT_ASSERT_VALUES_EQUAL(0, c2.size()); - UNIT_ASSERT_VALUES_EQUAL(4, c3.size()); - UNIT_ASSERT(c3.find(400) != c3.end()); - } + UNIT_ASSERT_VALUES_EQUAL(0, c2.size()); + UNIT_ASSERT_VALUES_EQUAL(4, c3.size()); + UNIT_ASSERT(c3.find(400) != c3.end()); + } } - struct TKey { - TKey() - : m_data(0) - { - } - - explicit TKey(int data) - : m_data(data) - { - } - - int m_data; - }; - - struct TKeyCmp { - bool operator()(TKey lhs, TKey rhs) const { - return lhs.m_data < rhs.m_data; - } - - bool operator()(TKey lhs, int rhs) const { - return lhs.m_data < rhs; - } - - bool operator()(int lhs, TKey rhs) const { - return lhs < rhs.m_data; - } + struct TKey { + TKey() + : m_data(0) + { + } + + explicit TKey(int data) + : m_data(data) + { + } + + int m_data; + }; + + struct TKeyCmp { + bool operator()(TKey lhs, TKey rhs) const { + return lhs.m_data < rhs.m_data; + } + + bool operator()(TKey lhs, int rhs) const { + return lhs.m_data < rhs; + } + + bool operator()(int lhs, TKey rhs) const { + return lhs < rhs.m_data; + } using is_transparent = void; - }; - - struct TKeyCmpPtr { - bool operator()(TKey const volatile* lhs, TKey const volatile* rhs) const { - return (*lhs).m_data < (*rhs).m_data; - } - - bool operator()(TKey const volatile* lhs, int rhs) const { - return (*lhs).m_data < rhs; - } - - bool operator()(int lhs, TKey const volatile* rhs) const { - return lhs < (*rhs).m_data; - } + }; + + struct TKeyCmpPtr { + bool operator()(TKey const volatile* lhs, TKey const volatile* rhs) const { + return (*lhs).m_data < (*rhs).m_data; + } + + bool operator()(TKey const volatile* lhs, int rhs) const { + return (*lhs).m_data < rhs; + } + + bool operator()(int lhs, TKey const volatile* rhs) const { + return lhs < (*rhs).m_data; + } using is_transparent = void; - }; - + }; + Y_UNIT_TEST(TestTemplateMethods) { - { + { using KeySet = TSet<TKey, TKeyCmp>; - KeySet keySet; - keySet.insert(TKey(1)); - keySet.insert(TKey(2)); - keySet.insert(TKey(3)); - keySet.insert(TKey(4)); - - UNIT_ASSERT(keySet.count(TKey(1)) == 1); - UNIT_ASSERT(keySet.count(1) == 1); - UNIT_ASSERT(keySet.count(5) == 0); - - UNIT_ASSERT(keySet.find(2) != keySet.end()); - UNIT_ASSERT(keySet.lower_bound(2) != keySet.end()); - UNIT_ASSERT(keySet.upper_bound(2) != keySet.end()); - UNIT_ASSERT(keySet.equal_range(2) != std::make_pair(keySet.begin(), keySet.end())); - - KeySet const& ckeySet = keySet; - UNIT_ASSERT(ckeySet.find(2) != ckeySet.end()); - UNIT_ASSERT(ckeySet.lower_bound(2) != ckeySet.end()); - UNIT_ASSERT(ckeySet.upper_bound(2) != ckeySet.end()); - UNIT_ASSERT(ckeySet.equal_range(2) != std::make_pair(ckeySet.begin(), ckeySet.end())); - } - - { + KeySet keySet; + keySet.insert(TKey(1)); + keySet.insert(TKey(2)); + keySet.insert(TKey(3)); + keySet.insert(TKey(4)); + + UNIT_ASSERT(keySet.count(TKey(1)) == 1); + UNIT_ASSERT(keySet.count(1) == 1); + UNIT_ASSERT(keySet.count(5) == 0); + + UNIT_ASSERT(keySet.find(2) != keySet.end()); + UNIT_ASSERT(keySet.lower_bound(2) != keySet.end()); + UNIT_ASSERT(keySet.upper_bound(2) != keySet.end()); + UNIT_ASSERT(keySet.equal_range(2) != std::make_pair(keySet.begin(), keySet.end())); + + KeySet const& ckeySet = keySet; + UNIT_ASSERT(ckeySet.find(2) != ckeySet.end()); + UNIT_ASSERT(ckeySet.lower_bound(2) != ckeySet.end()); + UNIT_ASSERT(ckeySet.upper_bound(2) != ckeySet.end()); + UNIT_ASSERT(ckeySet.equal_range(2) != std::make_pair(ckeySet.begin(), ckeySet.end())); + } + + { using KeySet = TSet<TKey*, TKeyCmpPtr>; - KeySet keySet; - TKey key1(1), key2(2), key3(3), key4(4); - keySet.insert(&key1); - keySet.insert(&key2); - keySet.insert(&key3); - keySet.insert(&key4); - - UNIT_ASSERT(keySet.count(1) == 1); - UNIT_ASSERT(keySet.count(5) == 0); - - UNIT_ASSERT(keySet.find(2) != keySet.end()); - UNIT_ASSERT(keySet.lower_bound(2) != keySet.end()); - UNIT_ASSERT(keySet.upper_bound(2) != keySet.end()); - UNIT_ASSERT(keySet.equal_range(2) != std::make_pair(keySet.begin(), keySet.end())); - - KeySet const& ckeySet = keySet; - UNIT_ASSERT(ckeySet.find(2) != ckeySet.end()); - UNIT_ASSERT(ckeySet.lower_bound(2) != ckeySet.end()); - UNIT_ASSERT(ckeySet.upper_bound(2) != ckeySet.end()); - UNIT_ASSERT(ckeySet.equal_range(2) != std::make_pair(ckeySet.begin(), ckeySet.end())); - } - { + KeySet keySet; + TKey key1(1), key2(2), key3(3), key4(4); + keySet.insert(&key1); + keySet.insert(&key2); + keySet.insert(&key3); + keySet.insert(&key4); + + UNIT_ASSERT(keySet.count(1) == 1); + UNIT_ASSERT(keySet.count(5) == 0); + + UNIT_ASSERT(keySet.find(2) != keySet.end()); + UNIT_ASSERT(keySet.lower_bound(2) != keySet.end()); + UNIT_ASSERT(keySet.upper_bound(2) != keySet.end()); + UNIT_ASSERT(keySet.equal_range(2) != std::make_pair(keySet.begin(), keySet.end())); + + KeySet const& ckeySet = keySet; + UNIT_ASSERT(ckeySet.find(2) != ckeySet.end()); + UNIT_ASSERT(ckeySet.lower_bound(2) != ckeySet.end()); + UNIT_ASSERT(ckeySet.upper_bound(2) != ckeySet.end()); + UNIT_ASSERT(ckeySet.equal_range(2) != std::make_pair(ckeySet.begin(), ckeySet.end())); + } + { using KeySet = TMultiSet<TKey, TKeyCmp>; - KeySet keySet; - keySet.insert(TKey(1)); - keySet.insert(TKey(2)); - keySet.insert(TKey(3)); - keySet.insert(TKey(4)); - - UNIT_ASSERT(keySet.count(TKey(1)) == 1); - UNIT_ASSERT(keySet.count(1) == 1); - UNIT_ASSERT(keySet.count(5) == 0); - - UNIT_ASSERT(keySet.find(2) != keySet.end()); - UNIT_ASSERT(keySet.lower_bound(2) != keySet.end()); - UNIT_ASSERT(keySet.upper_bound(2) != keySet.end()); - UNIT_ASSERT(keySet.equal_range(2) != std::make_pair(keySet.begin(), keySet.end())); - - KeySet const& ckeySet = keySet; - UNIT_ASSERT(ckeySet.find(2) != ckeySet.end()); - UNIT_ASSERT(ckeySet.lower_bound(2) != ckeySet.end()); - UNIT_ASSERT(ckeySet.upper_bound(2) != ckeySet.end()); - UNIT_ASSERT(ckeySet.equal_range(2) != std::make_pair(ckeySet.begin(), ckeySet.end())); - } - - { + KeySet keySet; + keySet.insert(TKey(1)); + keySet.insert(TKey(2)); + keySet.insert(TKey(3)); + keySet.insert(TKey(4)); + + UNIT_ASSERT(keySet.count(TKey(1)) == 1); + UNIT_ASSERT(keySet.count(1) == 1); + UNIT_ASSERT(keySet.count(5) == 0); + + UNIT_ASSERT(keySet.find(2) != keySet.end()); + UNIT_ASSERT(keySet.lower_bound(2) != keySet.end()); + UNIT_ASSERT(keySet.upper_bound(2) != keySet.end()); + UNIT_ASSERT(keySet.equal_range(2) != std::make_pair(keySet.begin(), keySet.end())); + + KeySet const& ckeySet = keySet; + UNIT_ASSERT(ckeySet.find(2) != ckeySet.end()); + UNIT_ASSERT(ckeySet.lower_bound(2) != ckeySet.end()); + UNIT_ASSERT(ckeySet.upper_bound(2) != ckeySet.end()); + UNIT_ASSERT(ckeySet.equal_range(2) != std::make_pair(ckeySet.begin(), ckeySet.end())); + } + + { using KeySet = TMultiSet<TKey const volatile*, TKeyCmpPtr>; - KeySet keySet; - TKey key1(1), key2(2), key3(3), key4(4); - keySet.insert(&key1); - keySet.insert(&key2); - keySet.insert(&key3); - keySet.insert(&key4); - - UNIT_ASSERT(keySet.count(1) == 1); - UNIT_ASSERT(keySet.count(5) == 0); - - UNIT_ASSERT(keySet.find(2) != keySet.end()); - UNIT_ASSERT(keySet.lower_bound(2) != keySet.end()); - UNIT_ASSERT(keySet.upper_bound(2) != keySet.end()); - UNIT_ASSERT(keySet.equal_range(2) != std::make_pair(keySet.begin(), keySet.end())); - - KeySet const& ckeySet = keySet; - UNIT_ASSERT(ckeySet.find(2) != ckeySet.end()); - UNIT_ASSERT(ckeySet.lower_bound(2) != ckeySet.end()); - UNIT_ASSERT(ckeySet.upper_bound(2) != ckeySet.end()); - UNIT_ASSERT(ckeySet.equal_range(2) != std::make_pair(ckeySet.begin(), ckeySet.end())); - } - } -} + KeySet keySet; + TKey key1(1), key2(2), key3(3), key4(4); + keySet.insert(&key1); + keySet.insert(&key2); + keySet.insert(&key3); + keySet.insert(&key4); + + UNIT_ASSERT(keySet.count(1) == 1); + UNIT_ASSERT(keySet.count(5) == 0); + + UNIT_ASSERT(keySet.find(2) != keySet.end()); + UNIT_ASSERT(keySet.lower_bound(2) != keySet.end()); + UNIT_ASSERT(keySet.upper_bound(2) != keySet.end()); + UNIT_ASSERT(keySet.equal_range(2) != std::make_pair(keySet.begin(), keySet.end())); + + KeySet const& ckeySet = keySet; + UNIT_ASSERT(ckeySet.find(2) != ckeySet.end()); + UNIT_ASSERT(ckeySet.lower_bound(2) != ckeySet.end()); + UNIT_ASSERT(ckeySet.upper_bound(2) != ckeySet.end()); + UNIT_ASSERT(ckeySet.equal_range(2) != std::make_pair(ckeySet.begin(), ckeySet.end())); + } + } +} diff --git a/util/generic/singleton.cpp b/util/generic/singleton.cpp index b193a589ab..eb5a0662f8 100644 --- a/util/generic/singleton.cpp +++ b/util/generic/singleton.cpp @@ -1,61 +1,61 @@ -#include "singleton.h" - -#include <util/system/spinlock.h> -#include <util/system/thread.h> +#include "singleton.h" + +#include <util/system/spinlock.h> +#include <util/system/thread.h> #include <util/system/sanitizers.h> - -#include <cstring> - -namespace { + +#include <cstring> + +namespace { static inline bool MyAtomicTryLock(TAtomic& a, TAtomicBase v) noexcept { - return AtomicCas(&a, v, 0); - } - + return AtomicCas(&a, v, 0); + } + static inline bool MyAtomicTryAndTryLock(TAtomic& a, TAtomicBase v) noexcept { - return (AtomicGet(a) == 0) && MyAtomicTryLock(a, v); - } - + return (AtomicGet(a) == 0) && MyAtomicTryLock(a, v); + } + static inline TAtomicBase MyThreadId() noexcept { - const TAtomicBase ret = TThread::CurrentThreadId(); - - if (ret) { - return ret; - } - - //clash almost impossible, ONLY if we have threads with ids 0 and 1! - return 1; - } -} - -void NPrivate::FillWithTrash(void* ptr, size_t len) { -#if defined(NDEBUG) + const TAtomicBase ret = TThread::CurrentThreadId(); + + if (ret) { + return ret; + } + + //clash almost impossible, ONLY if we have threads with ids 0 and 1! + return 1; + } +} + +void NPrivate::FillWithTrash(void* ptr, size_t len) { +#if defined(NDEBUG) Y_UNUSED(ptr); Y_UNUSED(len); -#else +#else if constexpr (NSan::TSanIsOn()) { Y_UNUSED(ptr); Y_UNUSED(len); } else { memset(ptr, 0xBA, len); } -#endif -} - +#endif +} + void NPrivate::LockRecursive(TAtomic& lock) noexcept { - const TAtomicBase id = MyThreadId(); - + const TAtomicBase id = MyThreadId(); + Y_VERIFY(AtomicGet(lock) != id, "recursive singleton initialization"); - - if (!MyAtomicTryLock(lock, id)) { - TSpinWait sw; - - do { - sw.Sleep(); - } while (!MyAtomicTryAndTryLock(lock, id)); - } -} - + + if (!MyAtomicTryLock(lock, id)) { + TSpinWait sw; + + do { + sw.Sleep(); + } while (!MyAtomicTryAndTryLock(lock, id)); + } +} + void NPrivate::UnlockRecursive(TAtomic& lock) noexcept { Y_VERIFY(AtomicGet(lock) == MyThreadId(), "unlock from another thread?!?!"); - AtomicUnlock(&lock); -} + AtomicUnlock(&lock); +} diff --git a/util/generic/singleton.h b/util/generic/singleton.h index 360925323d..f5fa047f5c 100644 --- a/util/generic/singleton.h +++ b/util/generic/singleton.h @@ -1,76 +1,76 @@ #pragma once - -#include <util/system/atexit.h> -#include <util/system/atomic.h> - -#include <new> + +#include <util/system/atexit.h> +#include <util/system/atomic.h> + +#include <new> #include <utility> - -template <class T> -struct TSingletonTraits { + +template <class T> +struct TSingletonTraits { static constexpr size_t Priority = 65536; -}; - -namespace NPrivate { - void FillWithTrash(void* ptr, size_t len); - +}; + +namespace NPrivate { + void FillWithTrash(void* ptr, size_t len); + void LockRecursive(TAtomic& lock) noexcept; void UnlockRecursive(TAtomic& lock) noexcept; - - template <class T> - void Destroyer(void* ptr) { - ((T*)ptr)->~T(); - FillWithTrash(ptr, sizeof(T)); - } - + + template <class T> + void Destroyer(void* ptr) { + ((T*)ptr)->~T(); + FillWithTrash(ptr, sizeof(T)); + } + template <class T, size_t P, class... TArgs> Y_NO_INLINE T* SingletonBase(T*& ptr, TArgs&&... args) { - alignas(T) static char buf[sizeof(T)]; - static TAtomic lock; - - LockRecursive(lock); - - auto ret = AtomicGet(ptr); - - try { - if (!ret) { + alignas(T) static char buf[sizeof(T)]; + static TAtomic lock; + + LockRecursive(lock); + + auto ret = AtomicGet(ptr); + + try { + if (!ret) { ret = ::new (buf) T(std::forward<TArgs>(args)...); - - try { - AtExit(Destroyer<T>, ret, P); - } catch (...) { - Destroyer<T>(ret); - - throw; - } - - AtomicSet(ptr, ret); - } - } catch (...) { - UnlockRecursive(lock); - - throw; - } - - UnlockRecursive(lock); - + + try { + AtExit(Destroyer<T>, ret, P); + } catch (...) { + Destroyer<T>(ret); + + throw; + } + + AtomicSet(ptr, ret); + } + } catch (...) { + UnlockRecursive(lock); + + throw; + } + + UnlockRecursive(lock); + return ret; - } + } template <class T, size_t P, class... TArgs> T* SingletonInt(TArgs&&... args) { - static_assert(sizeof(T) < 32000, "use HugeSingleton instead"); - - static T* ptr; - auto ret = AtomicGet(ptr); - - if (Y_UNLIKELY(!ret)) { + static_assert(sizeof(T) < 32000, "use HugeSingleton instead"); + + static T* ptr; + auto ret = AtomicGet(ptr); + + if (Y_UNLIKELY(!ret)) { ret = SingletonBase<T, P>(ptr, std::forward<TArgs>(args)...); - } - - return ret; - } - + } + + return ret; + } + template <class T> class TDefault { public: @@ -87,29 +87,29 @@ namespace NPrivate { private: T T_; }; - - template <class T> - struct THeapStore { + + template <class T> + struct THeapStore { template <class... TArgs> inline THeapStore(TArgs&&... args) : D(new T(std::forward<TArgs>(args)...)) - { - } - + { + } + inline ~THeapStore() { - delete D; - } - - T* D; - }; -} - -#define Y_DECLARE_SINGLETON_FRIEND() \ - template <class T, size_t P, class... TArgs> \ - friend T* ::NPrivate::SingletonInt(TArgs&&...); \ - template <class T, size_t P, class... TArgs> \ - friend T* ::NPrivate::SingletonBase(T*&, TArgs&&...); - + delete D; + } + + T* D; + }; +} + +#define Y_DECLARE_SINGLETON_FRIEND() \ + template <class T, size_t P, class... TArgs> \ + friend T* ::NPrivate::SingletonInt(TArgs&&...); \ + template <class T, size_t P, class... TArgs> \ + friend T* ::NPrivate::SingletonBase(T*&, TArgs&&...); + template <class T, class... TArgs> T* Singleton(TArgs&&... args) { return ::NPrivate::SingletonInt<T, TSingletonTraits<T>::Priority>(std::forward<TArgs>(args)...); @@ -117,20 +117,20 @@ T* Singleton(TArgs&&... args) { template <class T, class... TArgs> T* HugeSingleton(TArgs&&... args) { - return Singleton<::NPrivate::THeapStore<T>>(std::forward<TArgs>(args)...)->D; -} - + return Singleton<::NPrivate::THeapStore<T>>(std::forward<TArgs>(args)...)->D; +} + template <class T, size_t P, class... TArgs> T* SingletonWithPriority(TArgs&&... args) { return ::NPrivate::SingletonInt<T, P>(std::forward<TArgs>(args)...); -} - +} + template <class T, size_t P, class... TArgs> T* HugeSingletonWithPriority(TArgs&&... args) { - return SingletonWithPriority<::NPrivate::THeapStore<T>, P>(std::forward<TArgs>(args)...)->D; -} - + return SingletonWithPriority<::NPrivate::THeapStore<T>, P>(std::forward<TArgs>(args)...)->D; +} + template <class T> const T& Default() { - return *(::NPrivate::SingletonInt<typename ::NPrivate::TDefault<T>, TSingletonTraits<T>::Priority>()->Get()); -} + return *(::NPrivate::SingletonInt<typename ::NPrivate::TDefault<T>, TSingletonTraits<T>::Priority>()->Get()); +} diff --git a/util/generic/singleton_ut.cpp b/util/generic/singleton_ut.cpp index b168f149d5..35ba90cd76 100644 --- a/util/generic/singleton_ut.cpp +++ b/util/generic/singleton_ut.cpp @@ -1,17 +1,17 @@ -#include "singleton.h" - +#include "singleton.h" + #include <library/cpp/testing/unittest/registar.h> - + Y_UNIT_TEST_SUITE(TestSingleton) { - struct THuge { - char Buf[1000000]; - int V = 1234; - }; - + struct THuge { + char Buf[1000000]; + int V = 1234; + }; + Y_UNIT_TEST(TestHuge) { - UNIT_ASSERT_VALUES_EQUAL(*HugeSingleton<int>(), 0); - UNIT_ASSERT_VALUES_EQUAL(HugeSingleton<THuge>()->V, 1234); - } + UNIT_ASSERT_VALUES_EQUAL(*HugeSingleton<int>(), 0); + UNIT_ASSERT_VALUES_EQUAL(HugeSingleton<THuge>()->V, 1234); + } struct TWithParams { explicit TWithParams(const ui32 data1 = 0, const TString& data2 = TString()) @@ -43,4 +43,4 @@ Y_UNIT_TEST_SUITE(TestSingleton) { } UNIT_ASSERT_VALUES_EQUAL(Default<TWithParams>().Data1, 0); } -} +} diff --git a/util/generic/size_literals.h b/util/generic/size_literals.h index 52c16b2711..0b78b18687 100644 --- a/util/generic/size_literals.h +++ b/util/generic/size_literals.h @@ -6,19 +6,19 @@ // Unsigned literals -constexpr ui64 operator"" _KB(unsigned long long value) noexcept { +constexpr ui64 operator"" _KB(unsigned long long value) noexcept { return value * 1024; } -constexpr ui64 operator"" _MB(unsigned long long value) noexcept { +constexpr ui64 operator"" _MB(unsigned long long value) noexcept { return value * 1024_KB; } -constexpr ui64 operator"" _GB(unsigned long long value) noexcept { +constexpr ui64 operator"" _GB(unsigned long long value) noexcept { return value * 1024_MB; } -constexpr ui64 operator"" _TB(unsigned long long value) noexcept { +constexpr ui64 operator"" _TB(unsigned long long value) noexcept { return value * 1024_GB; } @@ -35,24 +35,24 @@ constexpr ui64 operator"" _EB(unsigned long long value) noexcept { namespace NPrivate { constexpr i64 SignedCast(ui64 value) { return value <= static_cast<ui64>(std::numeric_limits<i64>::max()) - ? static_cast<i64>(value) - : ythrow yexception() << "The resulting value " << value << " does not fit into the i64 type"; + ? static_cast<i64>(value) + : ythrow yexception() << "The resulting value " << value << " does not fit into the i64 type"; }; } -constexpr i64 operator"" _KBs(const unsigned long long value) noexcept { +constexpr i64 operator"" _KBs(const unsigned long long value) noexcept { return ::NPrivate::SignedCast(value * 1024); } -constexpr i64 operator"" _MBs(unsigned long long value) noexcept { +constexpr i64 operator"" _MBs(unsigned long long value) noexcept { return ::NPrivate::SignedCast(value * 1024_KB); } -constexpr i64 operator"" _GBs(unsigned long long value) noexcept { +constexpr i64 operator"" _GBs(unsigned long long value) noexcept { return ::NPrivate::SignedCast(value * 1024_MB); } -constexpr i64 operator"" _TBs(unsigned long long value) noexcept { +constexpr i64 operator"" _TBs(unsigned long long value) noexcept { return ::NPrivate::SignedCast(value * 1024_GB); } diff --git a/util/generic/stack.cpp b/util/generic/stack.cpp index 1b8783ab5a..7380615365 100644 --- a/util/generic/stack.cpp +++ b/util/generic/stack.cpp @@ -1 +1 @@ -#include "stack.h" +#include "stack.h" diff --git a/util/generic/stack.h b/util/generic/stack.h index 1b1a7b0547..dbcbf2b5c9 100644 --- a/util/generic/stack.h +++ b/util/generic/stack.h @@ -1,18 +1,18 @@ #pragma once - + #include "fwd.h" -#include "deque.h" - -#include <stack> - +#include "deque.h" + +#include <stack> + template <class T, class S> class TStack: public std::stack<T, S> { - using TBase = std::stack<T, S>; - -public: + using TBase = std::stack<T, S>; + +public: using TBase::TBase; - + inline explicit operator bool() const noexcept { return !this->empty(); } -}; +}; diff --git a/util/generic/stack_ut.cpp b/util/generic/stack_ut.cpp index 56a894cde6..248127d326 100644 --- a/util/generic/stack_ut.cpp +++ b/util/generic/stack_ut.cpp @@ -7,10 +7,10 @@ Y_UNIT_TEST_SUITE(TYStackTest) { TStack<int> s; UNIT_ASSERT(!s); - UNIT_ASSERT(s.empty()); + UNIT_ASSERT(s.empty()); s.push(100); s.push(200); - UNIT_ASSERT(s); + UNIT_ASSERT(s); UNIT_ASSERT(!s.empty()); } } diff --git a/util/generic/store_policy.cpp b/util/generic/store_policy.cpp index 33010c060a..bd445c891f 100644 --- a/util/generic/store_policy.cpp +++ b/util/generic/store_policy.cpp @@ -1 +1 @@ -#include "store_policy.h" +#include "store_policy.h" diff --git a/util/generic/store_policy.h b/util/generic/store_policy.h index 04aa3ca108..148821c70c 100644 --- a/util/generic/store_policy.h +++ b/util/generic/store_policy.h @@ -1,75 +1,75 @@ -#pragma once - +#pragma once + #include <utility> -#include "ptr.h" - -template <class TBase, class TCounter> -struct TWithRefCount: public TBase, public TRefCounted<TWithRefCount<TBase, TCounter>, TCounter> { - template <typename... Args> - inline TWithRefCount(Args&&... args) +#include "ptr.h" + +template <class TBase, class TCounter> +struct TWithRefCount: public TBase, public TRefCounted<TWithRefCount<TBase, TCounter>, TCounter> { + template <typename... Args> + inline TWithRefCount(Args&&... args) : TBase(std::forward<Args>(args)...) - { - } -}; - -template <class T> -struct TPtrPolicy { + { + } +}; + +template <class T> +struct TPtrPolicy { inline TPtrPolicy(T* t) - : T_(t) - { - } - + : T_(t) + { + } + inline T* Ptr() noexcept { return T_; } - inline const T* Ptr() const noexcept { - return T_; - } - + inline const T* Ptr() const noexcept { + return T_; + } + T* T_; -}; - -template <class T> -struct TEmbedPolicy { - template <typename... Args> - inline TEmbedPolicy(Args&&... args) +}; + +template <class T> +struct TEmbedPolicy { + template <typename... Args> + inline TEmbedPolicy(Args&&... args) : T_(std::forward<Args>(args)...) - { - } - - inline T* Ptr() noexcept { - return &T_; - } - - inline const T* Ptr() const noexcept { - return &T_; - } - - T T_; -}; - -template <class T, class TCounter> -struct TRefPolicy { - using THelper = TWithRefCount<T, TCounter>; - - template <typename... Args> - inline TRefPolicy(Args&&... args) + { + } + + inline T* Ptr() noexcept { + return &T_; + } + + inline const T* Ptr() const noexcept { + return &T_; + } + + T T_; +}; + +template <class T, class TCounter> +struct TRefPolicy { + using THelper = TWithRefCount<T, TCounter>; + + template <typename... Args> + inline TRefPolicy(Args&&... args) : T_(new THelper(std::forward<Args>(args)...)) - { - } - - inline T* Ptr() noexcept { - return T_.Get(); - } - - inline const T* Ptr() const noexcept { - return T_.Get(); - } - - TIntrusivePtr<THelper> T_; -}; - + { + } + + inline T* Ptr() noexcept { + return T_.Get(); + } + + inline const T* Ptr() const noexcept { + return T_.Get(); + } + + TIntrusivePtr<THelper> T_; +}; + /** * Storage class that can be handy for implementing proxies / adaptors that can * accept both lvalues and rvalues. In the latter case it's often required to @@ -94,7 +94,7 @@ struct TRefPolicy { * Look at `Reversed` in `adaptor.h` for real example. */ template <class T, bool IsReference = std::is_reference<T>::value> -struct TAutoEmbedOrPtrPolicy: TPtrPolicy<std::remove_reference_t<T>> { +struct TAutoEmbedOrPtrPolicy: TPtrPolicy<std::remove_reference_t<T>> { using TBase = TPtrPolicy<std::remove_reference_t<T>>; TAutoEmbedOrPtrPolicy(T& reference) @@ -104,7 +104,7 @@ struct TAutoEmbedOrPtrPolicy: TPtrPolicy<std::remove_reference_t<T>> { }; template <class T> -struct TAutoEmbedOrPtrPolicy<T, false>: TEmbedPolicy<T> { +struct TAutoEmbedOrPtrPolicy<T, false>: TEmbedPolicy<T> { using TBase = TEmbedPolicy<T>; TAutoEmbedOrPtrPolicy(T&& object) @@ -113,8 +113,8 @@ struct TAutoEmbedOrPtrPolicy<T, false>: TEmbedPolicy<T> { } }; -template <class T> -using TAtomicRefPolicy = TRefPolicy<T, TAtomicCounter>; - -template <class T> -using TSimpleRefPolicy = TRefPolicy<T, TSimpleCounter>; +template <class T> +using TAtomicRefPolicy = TRefPolicy<T, TAtomicCounter>; + +template <class T> +using TSimpleRefPolicy = TRefPolicy<T, TSimpleCounter>; diff --git a/util/generic/store_policy_ut.cpp b/util/generic/store_policy_ut.cpp index 4cc4c0c707..c9722203aa 100644 --- a/util/generic/store_policy_ut.cpp +++ b/util/generic/store_policy_ut.cpp @@ -14,7 +14,7 @@ Y_UNIT_TEST_SUITE(StorePolicy) { // const (**TAutoEmbedOrPtrPolicy<THolder<int>>(MakeHolder<int>(1)).Ptr())++; // ok - (**TAutoEmbedOrPtrPolicy<THolder<int>&>(a).Ptr())++; // ok + (**TAutoEmbedOrPtrPolicy<THolder<int>&>(a).Ptr())++; // ok const TVector<int> b = {0}; auto bValue = (*TAutoEmbedOrPtrPolicy<const TVector<int>&>(b).Ptr())[0]; // ok @@ -23,7 +23,7 @@ Y_UNIT_TEST_SUITE(StorePolicy) { } template <typename T, typename TFunc> - void FunctionTakingRefDefaultIsObject(T&& a, TFunc func) { + void FunctionTakingRefDefaultIsObject(T&& a, TFunc func) { TAutoEmbedOrPtrPolicy<T> refHolder(a); func(refHolder); } @@ -53,7 +53,7 @@ Y_UNIT_TEST_SUITE(StorePolicy) { } template <typename T, typename TFunc> - void FunctionTakingObjectDefaultObject(T&& a, TFunc func) { + void FunctionTakingObjectDefaultObject(T&& a, TFunc func) { TAutoEmbedOrPtrPolicy<T> objectHolder(std::forward<T>(a)); func(objectHolder); } diff --git a/util/generic/strbase.h b/util/generic/strbase.h index b978c09197..ab39fc7537 100644 --- a/util/generic/strbase.h +++ b/util/generic/strbase.h @@ -10,7 +10,7 @@ #include <util/charset/unidata.h> #include <util/system/platform.h> #include <util/system/yassert.h> - + #include <contrib/libs/libc_compat/string.h> #include <cctype> @@ -50,7 +50,7 @@ public: using const_iterator = const TCharType*; using const_reference = const TCharType&; - + template <typename TBase> struct TReverseIteratorBase { constexpr TReverseIteratorBase() noexcept = default; @@ -112,7 +112,7 @@ public: } return 0; } - + template <class TCharTraits> inline constexpr operator std::basic_string_view<TCharType, TCharTraits>() const { return std::basic_string_view<TCharType, TCharTraits>(data(), size()); @@ -122,7 +122,7 @@ public: inline explicit operator std::basic_string<TCharType, TCharTraits, Allocator>() const { return std::basic_string<TCharType, TCharTraits, Allocator>(Ptr(), Len()); } - + /** * @param Pointer to character inside the string, or nullptr. * @return Offset from string beginning (in chars), or npos on nullptr. @@ -130,7 +130,7 @@ public: inline size_t off(const TCharType* ret) const noexcept { return ret ? (size_t)(ret - Ptr()) : npos; } - + inline size_t IterOff(const_iterator it) const noexcept { return begin() <= it && end() > it ? size_t(it - begin()) : npos; } @@ -138,11 +138,11 @@ public: inline const_iterator begin() const noexcept { return Ptr(); } - + inline const_iterator end() const noexcept { return Ptr() + size(); } - + inline const_iterator cbegin() const noexcept { return begin(); } @@ -171,7 +171,7 @@ public: Y_ASSERT(!this->empty()); return Ptr()[Len() - 1]; } - + inline TCharType front() const noexcept { Y_ASSERT(!empty()); return Ptr()[0]; @@ -184,19 +184,19 @@ public: constexpr inline size_t size() const noexcept { return Len(); } - + constexpr inline bool is_null() const noexcept { return *Ptr() == 0; } - - Y_PURE_FUNCTION constexpr inline bool empty() const noexcept { + + Y_PURE_FUNCTION constexpr inline bool empty() const noexcept { return Len() == 0; } - + constexpr inline explicit operator bool() const noexcept { return !empty(); } - + public: // style-guide compliant methods constexpr const TCharType* Data() const noexcept { return Ptr(); @@ -206,7 +206,7 @@ public: // style-guide compliant methods return Len(); } - Y_PURE_FUNCTION constexpr bool Empty() const noexcept { + Y_PURE_FUNCTION constexpr bool Empty() const noexcept { return 0 == Len(); } @@ -221,7 +221,7 @@ public: static int compare(const TSelf& s1, const TSelf& s2) noexcept { return s1.AsStringView().compare(s2.AsStringView()); } - + static int compare(const TCharType* p, const TSelf& s2) noexcept { TCharType null{0}; return TStringViewWithTraits(p ? p : &null).compare(s2.AsStringView()); @@ -231,24 +231,24 @@ public: TCharType null{0}; return s1.AsStringView().compare(p ? p : &null); } - + static int compare(const TStringView s1, const TStringView s2) noexcept { - return TStringViewWithTraits(s1.data(), s1.size()).compare(TStringViewWithTraits(s2.data(), s2.size())); + return TStringViewWithTraits(s1.data(), s1.size()).compare(TStringViewWithTraits(s2.data(), s2.size())); } - + template <class T> inline int compare(const T& t) const noexcept { return compare(*this, t); } - + inline int compare(size_t p, size_t n, const TStringView t) const noexcept { return compare(LegacySubString(*this, p, n), t); } - + inline int compare(size_t p, size_t n, const TStringView t, size_t p1, size_t n1) const noexcept { return compare(LegacySubString(*this, p, n), LegacySubString(t, p1, n1)); } - + inline int compare(size_t p, size_t n, const TStringView t, size_t n1) const noexcept { return compare(LegacySubString(*this, p, n), LegacySubString(t, 0, n1)); } @@ -281,7 +281,7 @@ public: inline bool equal(const T& t) const noexcept { return equal(*this, t); } - + inline bool equal(size_t p, size_t n, const TStringView t) const noexcept { return equal(LegacySubString(*this, p, n), t); } @@ -297,19 +297,19 @@ public: static inline bool StartsWith(const TCharType* what, size_t whatLen, const TCharType* with, size_t withLen) noexcept { return withLen <= whatLen && TStringViewWithTraits(what, withLen) == TStringViewWithTraits(with, withLen); } - + static inline bool EndsWith(const TCharType* what, size_t whatLen, const TCharType* with, size_t withLen) noexcept { return withLen <= whatLen && TStringViewWithTraits(what + whatLen - withLen, withLen) == TStringViewWithTraits(with, withLen); } - + inline bool StartsWith(const TCharType* s, size_t n) const noexcept { return StartsWith(Ptr(), Len(), s, n); } - + inline bool StartsWith(const TStringView s) const noexcept { return StartsWith(s.data(), s.length()); } - + inline bool StartsWith(TCharType ch) const noexcept { return !empty() && TTraits::eq(*Ptr(), ch); } @@ -317,11 +317,11 @@ public: inline bool EndsWith(const TCharType* s, size_t n) const noexcept { return EndsWith(Ptr(), Len(), s, n); } - + inline bool EndsWith(const TStringView s) const noexcept { return EndsWith(s.data(), s.length()); } - + inline bool EndsWith(TCharType ch) const noexcept { return !empty() && TTraits::eq(Ptr()[Len() - 1], ch); } @@ -330,7 +330,7 @@ public: bool operator==(const TStringBase<TDerived2, TChar, TTraits2>& s2) const noexcept { return equal(*this, s2); } - + bool operator==(TStringView s2) const noexcept { return equal(*this, s2); } @@ -338,8 +338,8 @@ public: bool operator==(const TCharType* pc) const noexcept { return equal(*this, pc); } - -#ifndef __cpp_impl_three_way_comparison + +#ifndef __cpp_impl_three_way_comparison friend bool operator==(const TCharType* pc, const TSelf& s) noexcept { return equal(pc, s); } @@ -348,7 +348,7 @@ public: friend bool operator!=(const TSelf& s1, const TStringBase<TDerived2, TChar, TTraits2>& s2) noexcept { return !(s1 == s2); } - + friend bool operator!=(const TSelf& s1, TStringView s2) noexcept { return !(s1 == s2); } @@ -356,12 +356,12 @@ public: friend bool operator!=(const TSelf& s, const TCharType* pc) noexcept { return !(s == pc); } - + friend bool operator!=(const TCharType* pc, const TSelf& s) noexcept { return !(pc == s); } -#endif - +#endif + template <typename TDerived2, typename TTraits2> friend bool operator<(const TSelf& s1, const TStringBase<TDerived2, TChar, TTraits2>& s2) noexcept { return compare(s1, s2) < 0; @@ -374,16 +374,16 @@ public: friend bool operator<(const TSelf& s, const TCharType* pc) noexcept { return compare(s, pc) < 0; } - + friend bool operator<(const TCharType* pc, const TSelf& s) noexcept { return compare(pc, s) < 0; } - + template <typename TDerived2, typename TTraits2> friend bool operator<=(const TSelf& s1, const TStringBase<TDerived2, TChar, TTraits2>& s2) noexcept { return compare(s1, s2) <= 0; } - + friend bool operator<=(const TSelf& s1, TStringView s2) noexcept { return compare(s1, s2) <= 0; } @@ -391,16 +391,16 @@ public: friend bool operator<=(const TSelf& s, const TCharType* pc) noexcept { return compare(s, pc) <= 0; } - + friend bool operator<=(const TCharType* pc, const TSelf& s) noexcept { return compare(pc, s) <= 0; } - + template <typename TDerived2, typename TTraits2> friend bool operator>(const TSelf& s1, const TStringBase<TDerived2, TChar, TTraits2>& s2) noexcept { return compare(s1, s2) > 0; } - + friend bool operator>(const TSelf& s1, TStringView s2) noexcept { return compare(s1, s2) > 0; } @@ -408,11 +408,11 @@ public: friend bool operator>(const TSelf& s, const TCharType* pc) noexcept { return compare(s, pc) > 0; } - + friend bool operator>(const TCharType* pc, const TSelf& s) noexcept { return compare(pc, s) > 0; } - + template <typename TDerived2, typename TTraits2> friend bool operator>=(const TSelf& s1, const TStringBase<TDerived2, TChar, TTraits2>& s2) noexcept { return compare(s1, s2) >= 0; @@ -434,16 +434,16 @@ public: inline TCharType at(size_t pos) const noexcept { if (Y_LIKELY(pos < Len())) { return (Ptr())[pos]; - } + } return 0; } - + inline TCharType operator[](size_t pos) const noexcept { Y_ASSERT(pos < this->size()); return Ptr()[pos]; } - + //~~~~Search~~~~ /** * @return Position of the substring inside this string, or `npos` if not found. @@ -459,15 +459,15 @@ public: inline size_t find(TCharType c, size_t pos = 0) const noexcept { return AsStringView().find(c, pos); } - + inline size_t rfind(TCharType c) const noexcept { return AsStringView().rfind(c); } - + inline size_t rfind(TCharType c, size_t pos) const noexcept { if (pos == 0) { return npos; - } + } return AsStringView().rfind(c, pos - 1); } @@ -525,9 +525,9 @@ public: } inline size_t find_last_of(TCharType c, size_t pos = npos) const noexcept { - return find_last_of(&c, pos, 1); - } - + return find_last_of(&c, pos, 1); + } + inline size_t find_last_of(const TStringView set, size_t pos = npos) const noexcept { return find_last_of(set.data(), pos, set.length()); } @@ -535,7 +535,7 @@ public: inline size_t find_last_of(const TCharType* set, size_t pos, size_t n) const noexcept { return AsStringView().find_last_of(set, pos, n); } - + inline size_t find_last_not_of(TCharType c, size_t pos = npos) const noexcept { return AsStringView().find_last_not_of(c, pos); } @@ -551,28 +551,28 @@ public: inline size_t copy(TCharType* pc, size_t n, size_t pos) const { if (pos > Len()) { throw std::out_of_range("TStringBase::copy"); - } - + } + return CopyImpl(pc, n, pos); } - + inline size_t copy(TCharType* pc, size_t n) const noexcept { return CopyImpl(pc, n, 0); } - + inline size_t strcpy(TCharType* pc, size_t n) const noexcept { if (n) { n = copy(pc, n - 1); pc[n] = 0; - } - + } + return n; } - + inline TDerived copy() const Y_WARN_UNUSED_RESULT { return TDerived(Ptr(), Len()); } - + // ~~~ Partial copy ~~~~ TDerived substr(size_t pos, size_t n = npos) const Y_WARN_UNUSED_RESULT { return TDerived(*This(), pos, n); @@ -580,15 +580,15 @@ public: private: using GenericFinder = const TCharType* (*)(const TCharType*, size_t, const TCharType*, size_t); - + TStringViewWithTraits AsStringView() const { return static_cast<TStringViewWithTraits>(*this); - } - + } + constexpr inline const TCharType* Ptr() const noexcept { return This()->data(); } - + constexpr inline size_t Len() const noexcept { return This()->length(); } @@ -599,9 +599,9 @@ private: inline size_t CopyImpl(TCharType* pc, size_t n, size_t pos) const noexcept { const size_t toCopy = Min(Len() - pos, n); - + TTraits::copy(pc, Ptr() + pos, toCopy); - + return toCopy; } -}; +}; diff --git a/util/generic/strbuf.cpp b/util/generic/strbuf.cpp index 4a856016ad..668602ca16 100644 --- a/util/generic/strbuf.cpp +++ b/util/generic/strbuf.cpp @@ -1,9 +1,9 @@ -#include "strbuf.h" +#include "strbuf.h" #include <util/stream/output.h> #include <ostream> -std::ostream& operator<<(std::ostream& os, TStringBuf buf) { +std::ostream& operator<<(std::ostream& os, TStringBuf buf) { os.write(buf.data(), buf.size()); return os; } diff --git a/util/generic/strbuf.h b/util/generic/strbuf.h index 4c140ccbe4..70b9360d58 100644 --- a/util/generic/strbuf.h +++ b/util/generic/strbuf.h @@ -1,17 +1,17 @@ #pragma once - + #include "fwd.h" #include "strbase.h" -#include "utility.h" -#include "typetraits.h" - +#include "utility.h" +#include "typetraits.h" + #include <string_view> using namespace std::string_view_literals; template <typename TCharType, typename TTraits> -class TBasicStringBuf: public std::basic_string_view<TCharType>, - public TStringBase<TBasicStringBuf<TCharType, TTraits>, TCharType, TTraits> { +class TBasicStringBuf: public std::basic_string_view<TCharType>, + public TStringBase<TBasicStringBuf<TCharType, TTraits>, TCharType, TTraits> { private: using TdSelf = TBasicStringBuf; using TBase = TStringBase<TdSelf, TCharType, TTraits>; @@ -24,13 +24,13 @@ public: //Resolving some ambiguity between TStringBase and std::basic_string_view //for typenames using typename TStringView::const_iterator; - using typename TStringView::const_reference; + using typename TStringView::const_reference; using typename TStringView::const_reverse_iterator; - using typename TStringView::iterator; + using typename TStringView::iterator; using typename TStringView::reference; - using typename TStringView::reverse_iterator; - using typename TStringView::size_type; - using typename TStringView::value_type; + using typename TStringView::reverse_iterator; + using typename TStringView::size_type; + using typename TStringView::value_type; //for constants using TStringView::npos; @@ -39,14 +39,14 @@ public: using TStringView::begin; using TStringView::cbegin; using TStringView::cend; - using TStringView::crbegin; - using TStringView::crend; - using TStringView::end; + using TStringView::crbegin; + using TStringView::crend; + using TStringView::end; using TStringView::rbegin; using TStringView::rend; - using TStringView::data; - using TStringView::empty; + using TStringView::data; + using TStringView::empty; using TStringView::size; using TStringView::operator[]; @@ -57,7 +57,7 @@ public: * while std::string_view throws std::out_of_range. */ using TBase::at; - using TStringView::back; + using TStringView::back; using TStringView::front; using TStringView::find; @@ -66,11 +66,11 @@ public: * TBase::*find* methods take into account TCharTraits, * while TTStringView::*find* would use default std::char_traits. */ - using TBase::find_first_not_of; + using TBase::find_first_not_of; using TBase::find_first_of; - using TBase::find_last_not_of; + using TBase::find_last_not_of; using TBase::find_last_of; - using TBase::rfind; + using TBase::rfind; using TStringView::copy; /* @@ -101,7 +101,7 @@ public: : TStringView(data, size) { } - + constexpr TBasicStringBuf(const TCharType* data) noexcept /* * WARN: TBase::StrLen properly handles nullptr, @@ -110,18 +110,18 @@ public: : TStringView(data, TBase::StrLen(data)) { } - + constexpr inline TBasicStringBuf(const TCharType* beg, const TCharType* end) noexcept : TStringView(beg, end - beg) - { - } + { + } template <typename D, typename T> inline TBasicStringBuf(const TStringBase<D, TCharType, T>& str) noexcept : TStringView(str.data(), str.size()) { } - + template <typename T, typename A> inline TBasicStringBuf(const std::basic_string<TCharType, T, A>& str) noexcept : TStringView(str) @@ -134,7 +134,7 @@ public: { } - constexpr inline TBasicStringBuf() noexcept { + constexpr inline TBasicStringBuf() noexcept { /* * WARN: * This ctor can not be defaulted due to the following feature of default initialization: @@ -144,7 +144,7 @@ public: * This means, that a class with default ctor can not be a constant member of another class with default ctor. */ } - + inline TBasicStringBuf(const TBasicStringBuf& src, size_t pos, size_t n) noexcept : TBasicStringBuf(src) { @@ -156,7 +156,7 @@ public: { } - Y_PURE_FUNCTION inline TBasicStringBuf SubString(size_t pos, size_t n) const noexcept { + Y_PURE_FUNCTION inline TBasicStringBuf SubString(size_t pos, size_t n) const noexcept { pos = Min(pos, size()); n = Min(n, size() - pos); return TBasicStringBuf(data() + pos, n); @@ -170,7 +170,7 @@ public: constexpr bool IsInited() const noexcept { return data() != nullptr; } - + public: /** * Tries to split string in two parts using given delimiter character. @@ -186,7 +186,7 @@ public: inline bool TrySplit(TCharType delim, TdSelf& l, TdSelf& r) const noexcept { return TrySplitOn(TBase::find(delim), l, r); } - + /** * Tries to split string in two parts using given delimiter character. * Searches for the delimiter, scanning string from the end. @@ -201,7 +201,7 @@ public: inline bool TryRSplit(TCharType delim, TdSelf& l, TdSelf& r) const noexcept { return TrySplitOn(TBase::rfind(delim), l, r); } - + /** * Tries to split string in two parts using given delimiter sequence. * Searches for the delimiter, scanning string from the beginning. @@ -279,9 +279,9 @@ public: if (!TrySplitOn(pos, l, r, len)) { l = *this; r = TdSelf(); - } + } } - + bool TrySplitAt(size_t pos, TdSelf& l, TdSelf& r) const noexcept { return TrySplitOn(pos, l, r, 0); } @@ -297,22 +297,22 @@ public: */ public: - Y_PURE_FUNCTION inline TdSelf After(TCharType c) const noexcept { + Y_PURE_FUNCTION inline TdSelf After(TCharType c) const noexcept { TdSelf l, r; return TrySplit(c, l, r) ? r : *this; } - - Y_PURE_FUNCTION inline TdSelf Before(TCharType c) const noexcept { + + Y_PURE_FUNCTION inline TdSelf Before(TCharType c) const noexcept { TdSelf l, r; return TrySplit(c, l, r) ? l : *this; } - Y_PURE_FUNCTION inline TdSelf RAfter(TCharType c) const noexcept { + Y_PURE_FUNCTION inline TdSelf RAfter(TCharType c) const noexcept { TdSelf l, r; return TryRSplit(c, l, r) ? r : *this; } - Y_PURE_FUNCTION inline TdSelf RBefore(TCharType c) const noexcept { + Y_PURE_FUNCTION inline TdSelf RBefore(TCharType c) const noexcept { TdSelf l, r; return TryRSplit(c, l, r) ? l : *this; } @@ -392,31 +392,31 @@ public: bool NextTok(TCharType delim, TdSelf& tok) { return NextTokTemplate(delim, tok); } - + bool NextTok(TdSelf delim, TdSelf& tok) { return NextTokTemplate(delim, tok); } - + bool RNextTok(TCharType delim, TdSelf& tok) { return RNextTokTemplate(delim, tok); - } - + } + bool RNextTok(TdSelf delim, TdSelf& tok) { return RNextTokTemplate(delim, tok); } - bool ReadLine(TdSelf& tok) { - if (NextTok('\n', tok)) { - while (!tok.empty() && tok.back() == '\r') { + bool ReadLine(TdSelf& tok) { + if (NextTok('\n', tok)) { + while (!tok.empty() && tok.back() == '\r') { tok.remove_suffix(1); - } - - return true; - } - - return false; - } - + } + + return true; + } + + return false; + } + TdSelf NextTok(TCharType delim) { return NextTokTemplate(delim); } @@ -432,20 +432,20 @@ public: TdSelf RNextTok(TdSelf delim) { return RNextTokTemplate(delim); } - + public: // string subsequences /// Cut last @c shift characters (or less if length is less than @c shift) inline TdSelf& Chop(size_t shift) noexcept { this->remove_suffix(std::min(shift, size())); return *this; } - + /// Cut first @c shift characters (or less if length is less than @c shift) inline TdSelf& Skip(size_t shift) noexcept { this->remove_prefix(std::min(shift, size())); return *this; } - + /// Sets the start pointer to a position relative to the end inline TdSelf& RSeek(size_t tailSize) noexcept { if (size() > tailSize) { @@ -465,24 +465,24 @@ public: // string subsequences *this = TStringView::substr(0, targetSize); //WARN: removing TStringView:: will lead to an infinite recursion return *this; } - - Y_PURE_FUNCTION inline TdSelf SubStr(size_t beg) const noexcept { + + Y_PURE_FUNCTION inline TdSelf SubStr(size_t beg) const noexcept { return TdSelf(*this).Skip(beg); } - - Y_PURE_FUNCTION inline TdSelf SubStr(size_t beg, size_t len) const noexcept { + + Y_PURE_FUNCTION inline TdSelf SubStr(size_t beg, size_t len) const noexcept { return SubStr(beg).Trunc(len); } - Y_PURE_FUNCTION inline TdSelf Head(size_t pos) const noexcept { + Y_PURE_FUNCTION inline TdSelf Head(size_t pos) const noexcept { return TdSelf(*this).Trunc(pos); } - Y_PURE_FUNCTION inline TdSelf Tail(size_t pos) const noexcept { + Y_PURE_FUNCTION inline TdSelf Tail(size_t pos) const noexcept { return SubStr(pos); } - Y_PURE_FUNCTION inline TdSelf Last(size_t len) const noexcept { + Y_PURE_FUNCTION inline TdSelf Last(size_t len) const noexcept { return TdSelf(*this).RSeek(len); } @@ -534,6 +534,6 @@ private: l = TdSelf(); } } -}; - -std::ostream& operator<<(std::ostream& os, TStringBuf buf); +}; + +std::ostream& operator<<(std::ostream& os, TStringBuf buf); diff --git a/util/generic/strbuf_ut.cpp b/util/generic/strbuf_ut.cpp index 582cfff5c4..69cde785af 100644 --- a/util/generic/strbuf_ut.cpp +++ b/util/generic/strbuf_ut.cpp @@ -1,13 +1,13 @@ -#include "strbuf.h" - +#include "strbuf.h" + #include <library/cpp/testing/unittest/registar.h> - + #include <string_view> Y_UNIT_TEST_SUITE(TStrBufTest) { Y_UNIT_TEST(TestConstructorsAndOperators) { - TStringBuf str("qwerty"); - + TStringBuf str("qwerty"); + UNIT_ASSERT_EQUAL(*str.data(), 'q'); UNIT_ASSERT_EQUAL(str.size(), 6); @@ -25,8 +25,8 @@ Y_UNIT_TEST_SUITE(TStrBufTest) { std::string_view fromStringBuf = fromStringView; UNIT_ASSERT_EQUAL(helloWorld.data(), fromStringBuf.data()); UNIT_ASSERT_EQUAL(helloWorld.size(), fromStringBuf.size()); - } - + } + Y_UNIT_TEST(TestConstExpr) { static constexpr TStringBuf str1("qwe\0rty", 7); static constexpr TStringBuf str2(str1.data(), str1.size()); @@ -50,8 +50,8 @@ Y_UNIT_TEST_SUITE(TStrBufTest) { } Y_UNIT_TEST(TestAfter) { - TStringBuf str("qwerty"); - + TStringBuf str("qwerty"); + UNIT_ASSERT_VALUES_EQUAL(str.After('w'), TStringBuf("erty")); UNIT_ASSERT_VALUES_EQUAL(str.After('x'), TStringBuf("qwerty")); UNIT_ASSERT_VALUES_EQUAL(str.After('y'), TStringBuf()); @@ -60,17 +60,17 @@ Y_UNIT_TEST_SUITE(TStrBufTest) { // Also works properly on empty strings TStringBuf empty; UNIT_ASSERT_STRINGS_EQUAL(empty.After('x'), empty); - } - + } + Y_UNIT_TEST(TestBefore) { - TStringBuf str("qwerty"); - + TStringBuf str("qwerty"); + UNIT_ASSERT_VALUES_EQUAL(str.Before('w'), TStringBuf("q")); UNIT_ASSERT_VALUES_EQUAL(str.Before('x'), TStringBuf("qwerty")); UNIT_ASSERT_VALUES_EQUAL(str.Before('y'), TStringBuf("qwert")); UNIT_ASSERT_VALUES_EQUAL(str.Before('q'), TStringBuf()); - } - + } + Y_UNIT_TEST(TestRAfterBefore) { TStringBuf str("a/b/c"); UNIT_ASSERT_STRINGS_EQUAL(str.RAfter('/'), "c"); @@ -98,13 +98,13 @@ Y_UNIT_TEST_SUITE(TStrBufTest) { // SkipPrefix() TStringBuf a = "abcdef"; - UNIT_ASSERT(a.SkipPrefix("a") && a == "bcdef"); - UNIT_ASSERT(a.SkipPrefix("bc") && a == "def"); - UNIT_ASSERT(a.SkipPrefix("") && a == "def"); + UNIT_ASSERT(a.SkipPrefix("a") && a == "bcdef"); + UNIT_ASSERT(a.SkipPrefix("bc") && a == "def"); + UNIT_ASSERT(a.SkipPrefix("") && a == "def"); UNIT_ASSERT(!a.SkipPrefix("xyz") && a == "def"); UNIT_ASSERT(!a.SkipPrefix("defg") && a == "def"); - UNIT_ASSERT(a.SkipPrefix("def") && a == ""); - UNIT_ASSERT(a.SkipPrefix("") && a == ""); + UNIT_ASSERT(a.SkipPrefix("def") && a == ""); + UNIT_ASSERT(a.SkipPrefix("") && a == ""); UNIT_ASSERT(!a.SkipPrefix("def") && a == ""); } @@ -125,20 +125,20 @@ Y_UNIT_TEST_SUITE(TStrBufTest) { // ChopSuffix() TStringBuf a = "abcdef"; - UNIT_ASSERT(a.ChopSuffix("f") && a == "abcde"); - UNIT_ASSERT(a.ChopSuffix("de") && a == "abc"); - UNIT_ASSERT(a.ChopSuffix("") && a == "abc"); + UNIT_ASSERT(a.ChopSuffix("f") && a == "abcde"); + UNIT_ASSERT(a.ChopSuffix("de") && a == "abc"); + UNIT_ASSERT(a.ChopSuffix("") && a == "abc"); UNIT_ASSERT(!a.ChopSuffix("xyz") && a == "abc"); UNIT_ASSERT(!a.ChopSuffix("abcd") && a == "abc"); - UNIT_ASSERT(a.ChopSuffix("abc") && a == ""); - UNIT_ASSERT(a.ChopSuffix("") && a == ""); + UNIT_ASSERT(a.ChopSuffix("abc") && a == ""); + UNIT_ASSERT(a.ChopSuffix("") && a == ""); UNIT_ASSERT(!a.ChopSuffix("abc") && a == ""); } Y_UNIT_TEST(TestEmpty) { UNIT_ASSERT(TStringBuf().empty()); UNIT_ASSERT(!TStringBuf("q").empty()); - } + } Y_UNIT_TEST(TestShift) { TStringBuf qw("qwerty"); @@ -177,14 +177,14 @@ Y_UNIT_TEST_SUITE(TStrBufTest) { } Y_UNIT_TEST(TestNextTok) { - TStringBuf buf("12q45q"); - TStringBuf tok; - - UNIT_ASSERT(buf.NextTok('q', tok) && tok == "12"); - UNIT_ASSERT(buf.NextTok('q', tok) && tok == "45"); - UNIT_ASSERT(!buf.NextTok('q', tok)); - } - + TStringBuf buf("12q45q"); + TStringBuf tok; + + UNIT_ASSERT(buf.NextTok('q', tok) && tok == "12"); + UNIT_ASSERT(buf.NextTok('q', tok) && tok == "45"); + UNIT_ASSERT(!buf.NextTok('q', tok)); + } + Y_UNIT_TEST(TestNextStringTok) { TStringBuf buf1("a@@b@@c"); UNIT_ASSERT_EQUAL(buf1.NextTok("@@"), TStringBuf("a")); @@ -204,9 +204,9 @@ Y_UNIT_TEST_SUITE(TStrBufTest) { } Y_UNIT_TEST(TestReadLine) { - TStringBuf buf("12\n45\r\n\r\n23"); - TStringBuf tok; - + TStringBuf buf("12\n45\r\n\r\n23"); + TStringBuf tok; + buf.ReadLine(tok); UNIT_ASSERT_VALUES_EQUAL(tok, "12"); @@ -219,9 +219,9 @@ Y_UNIT_TEST_SUITE(TStrBufTest) { buf.ReadLine(tok); UNIT_ASSERT_VALUES_EQUAL(tok, "23"); - UNIT_ASSERT(!buf.ReadLine(tok)); - } - + UNIT_ASSERT(!buf.ReadLine(tok)); + } + Y_UNIT_TEST(TestRFind) { TStringBuf buf1 = "123123456"; UNIT_ASSERT_EQUAL(buf1.rfind('3'), 5); @@ -346,7 +346,7 @@ Y_UNIT_TEST_SUITE(TStrBufTest) { s.Trunc(0); UNIT_ASSERT_STRINGS_EQUAL(s, ""); } -} +} Y_UNIT_TEST_SUITE(TWtrBufTest) { Y_UNIT_TEST(TestConstExpr) { diff --git a/util/generic/strfcpy.cpp b/util/generic/strfcpy.cpp index 771afbbc64..19b4da493e 100644 --- a/util/generic/strfcpy.cpp +++ b/util/generic/strfcpy.cpp @@ -28,23 +28,23 @@ * Copy string src to buffer dst of size dsize. At most dsize-1 * chars will be copied. Always NUL terminates (unless dsize == 0). */ -void strfcpy(char* dst, const char* src, size_t dsize) +void strfcpy(char* dst, const char* src, size_t dsize) { - size_t nleft = dsize; + size_t nleft = dsize; - /* Copy as many bytes as will fit. */ - if (nleft != 0) { - while (--nleft != 0) { - if ((*dst++ = *src++) == '\0') { - break; - } - } - } + /* Copy as many bytes as will fit. */ + if (nleft != 0) { + while (--nleft != 0) { + if ((*dst++ = *src++) == '\0') { + break; + } + } + } - /* Not enough room in dst, add NUL */ - if (nleft == 0) { - if (dsize != 0) { - *dst = '\0'; /* NUL-terminate dst */ - } - } + /* Not enough room in dst, add NUL */ + if (nleft == 0) { + if (dsize != 0) { + *dst = '\0'; /* NUL-terminate dst */ + } + } } diff --git a/util/generic/strfcpy.h b/util/generic/strfcpy.h index db6e11c926..8a95bc3df2 100644 --- a/util/generic/strfcpy.h +++ b/util/generic/strfcpy.h @@ -14,4 +14,4 @@ #include <stddef.h> -void strfcpy(char* dst, const char* src, size_t n); +void strfcpy(char* dst, const char* src, size_t n); diff --git a/util/generic/string.cpp b/util/generic/string.cpp index 2cb82403f2..3c655f1f66 100644 --- a/util/generic/string.cpp +++ b/util/generic/string.cpp @@ -2,33 +2,33 @@ #include <util/string/ascii.h> #include <util/system/sanitizers.h> -#include <util/system/sys_alloc.h> -#include <util/charset/wide.h> +#include <util/system/sys_alloc.h> +#include <util/charset/wide.h> -#include <iostream> -#include <cctype> - -alignas(32) const char NULL_STRING_REPR[128] = {0}; +#include <iostream> +#include <cctype> + +alignas(32) const char NULL_STRING_REPR[128] = {0}; std::ostream& operator<<(std::ostream& os, const TString& s) { return os.write(s.data(), s.size()); -} - +} + std::istream& operator>>(std::istream& is, TString& s) { - return is >> s.MutRef(); + return is >> s.MutRef(); } -template <> +template <> bool TBasicString<char, std::char_traits<char>>::to_lower(size_t pos, size_t n) { return Transform([](size_t, char c) { return AsciiToLower(c); }, pos, n); } -template <> +template <> bool TBasicString<char, std::char_traits<char>>::to_upper(size_t pos, size_t n) { return Transform([](size_t, char c) { return AsciiToUpper(c); }, pos, n); } -template <> +template <> bool TBasicString<char, std::char_traits<char>>::to_title(size_t pos, size_t n) { if (n == 0) { return false; @@ -37,51 +37,51 @@ bool TBasicString<char, std::char_traits<char>>::to_title(size_t pos, size_t n) return to_lower(pos + 1, n - 1) || changed; } -template <> +template <> TUtf16String& TBasicString<wchar16, std::char_traits<wchar16>>::AppendAscii(const ::TStringBuf& s) { ReserveAndResize(size() + s.size()); - + auto dst = begin() + size() - s.size(); - + for (const char* src = s.data(); dst != end(); ++dst, ++src) { *dst = static_cast<wchar16>(*src); } - + return *this; } -template <> +template <> TUtf16String& TBasicString<wchar16, std::char_traits<wchar16>>::AppendUtf8(const ::TStringBuf& s) { size_t oldSize = size(); ReserveAndResize(size() + s.size() * 4); size_t written = 0; size_t pos = UTF8ToWideImpl(s.data(), s.size(), begin() + oldSize, written); - if (pos != s.size()) { + if (pos != s.size()) { ythrow yexception() << "failed to decode UTF-8 string at pos " << pos << ::NDetail::InStringMsg(s.data(), s.size()); - } + } resize(oldSize + written); return *this; } -template <> +template <> bool TBasicString<wchar16, std::char_traits<wchar16>>::to_lower(size_t pos, size_t n) { return ToLower(*this, pos, n); } -template <> +template <> bool TBasicString<wchar16, std::char_traits<wchar16>>::to_upper(size_t pos, size_t n) { return ToUpper(*this, pos, n); } -template <> +template <> bool TBasicString<wchar16, std::char_traits<wchar16>>::to_title(size_t pos, size_t n) { return ToTitle(*this, pos, n); } -template <> +template <> TUtf32String& TBasicString<wchar32, std::char_traits<wchar32>>::AppendAscii(const ::TStringBuf& s) { ReserveAndResize(size() + s.size()); @@ -95,7 +95,7 @@ TBasicString<wchar32, std::char_traits<wchar32>>::AppendAscii(const ::TStringBuf return *this; } -template <> +template <> TBasicString<char, std::char_traits<char>>& TBasicString<char, std::char_traits<char>>::AppendUtf16(const ::TWtringBuf& s) { const size_t oldSize = size(); @@ -109,22 +109,22 @@ TBasicString<char, std::char_traits<char>>::AppendUtf16(const ::TWtringBuf& s) { return *this; } -template <> +template <> TUtf32String& TBasicString<wchar32, std::char_traits<wchar32>>::AppendUtf8(const ::TStringBuf& s) { size_t oldSize = size(); ReserveAndResize(size() + s.size() * 4); size_t written = 0; size_t pos = UTF8ToWideImpl(s.data(), s.size(), begin() + oldSize, written); - if (pos != s.size()) { + if (pos != s.size()) { ythrow yexception() << "failed to decode UTF-8 string at pos " << pos << ::NDetail::InStringMsg(s.data(), s.size()); - } + } resize(oldSize + written); return *this; } -template <> +template <> TUtf32String& TBasicString<wchar32, std::char_traits<wchar32>>::AppendUtf16(const ::TWtringBuf& s) { size_t oldSize = size(); @@ -140,17 +140,17 @@ TBasicString<wchar32, std::char_traits<wchar32>>::AppendUtf16(const ::TWtringBuf return *this; } -template <> +template <> bool TBasicString<wchar32, std::char_traits<wchar32>>::to_lower(size_t pos, size_t n) { return ToLower(*this, pos, n); } -template <> +template <> bool TBasicString<wchar32, std::char_traits<wchar32>>::to_upper(size_t pos, size_t n) { return ToUpper(*this, pos, n); } -template <> +template <> bool TBasicString<wchar32, std::char_traits<wchar32>>::to_title(size_t pos, size_t n) { return ToTitle(*this, pos, n); } diff --git a/util/generic/string.h b/util/generic/string.h index 77a7523596..8cd8aa6917 100644 --- a/util/generic/string.h +++ b/util/generic/string.h @@ -1,18 +1,18 @@ #pragma once -#include <cstddef> -#include <cstring> +#include <cstddef> +#include <cstring> #include <stlfwd> #include <stdexcept> -#include <string> +#include <string> #include <string_view> #include <util/system/yassert.h> #include <util/system/atomic.h> - -#include "ptr.h" + +#include "ptr.h" #include "utility.h" -#include "bitops.h" +#include "bitops.h" #include "explicit_type.h" #include "reserve.h" #include "singleton.h" @@ -21,87 +21,87 @@ #include "string_hash.h" #if defined(address_sanitizer_enabled) || defined(thread_sanitizer_enabled) - #include "hide_ptr.h" + #include "hide_ptr.h" +#endif + +template <class TCharType, class TCharTraits, class TAllocator> +void ResizeUninitialized(std::basic_string<TCharType, TCharTraits, TAllocator>& s, size_t len) { +#if defined(_YNDX_LIBCXX_ENABLE_STRING_RESIZE_UNINITIALIZED) + s.resize_uninitialized(len); +#else + s.resize(len); #endif +} + +#define Y_NOEXCEPT + +#ifndef TSTRING_IS_STD_STRING +template <class T> +class TStringPtrOps { +public: + static inline void Ref(T* t) noexcept { + if (t != T::NullStr()) { + t->Ref(); + } + } + + static inline void UnRef(T* t) noexcept { + if (t != T::NullStr()) { + t->UnRef(); + } + } + + static inline long RefCount(const T* t) noexcept { + if (t == T::NullStr()) { + return -1; + } -template <class TCharType, class TCharTraits, class TAllocator> -void ResizeUninitialized(std::basic_string<TCharType, TCharTraits, TAllocator>& s, size_t len) { -#if defined(_YNDX_LIBCXX_ENABLE_STRING_RESIZE_UNINITIALIZED) - s.resize_uninitialized(len); -#else - s.resize(len); -#endif -} - -#define Y_NOEXCEPT - -#ifndef TSTRING_IS_STD_STRING -template <class T> -class TStringPtrOps { -public: - static inline void Ref(T* t) noexcept { - if (t != T::NullStr()) { - t->Ref(); - } - } - - static inline void UnRef(T* t) noexcept { - if (t != T::NullStr()) { - t->UnRef(); - } - } - - static inline long RefCount(const T* t) noexcept { - if (t == T::NullStr()) { - return -1; - } - - return t->RefCount(); - } -}; - -alignas(32) extern const char NULL_STRING_REPR[128]; - -struct TRefCountHolder { - TAtomicCounter C = 1; -}; - -template <class B> -struct TStdString: public TRefCountHolder, public B { - template <typename... Args> - inline TStdString(Args&&... args) - : B(std::forward<Args>(args)...) - { - } - - inline bool IsNull() const noexcept { - return this == NullStr(); - } - - static TStdString* NullStr() noexcept { + return t->RefCount(); + } +}; + +alignas(32) extern const char NULL_STRING_REPR[128]; + +struct TRefCountHolder { + TAtomicCounter C = 1; +}; + +template <class B> +struct TStdString: public TRefCountHolder, public B { + template <typename... Args> + inline TStdString(Args&&... args) + : B(std::forward<Args>(args)...) + { + } + + inline bool IsNull() const noexcept { + return this == NullStr(); + } + + static TStdString* NullStr() noexcept { #ifdef _LIBCPP_VERSION - return (TStdString*)NULL_STRING_REPR; + return (TStdString*)NULL_STRING_REPR; #else return Singleton<TStdString>(); #endif - } - + } + private: friend TStringPtrOps<TStdString>; - inline void Ref() noexcept { - C.Inc(); - } - - inline void UnRef() noexcept { - if (C.Val() == 1 || C.Dec() == 0) { - delete this; - } - } - - inline long RefCount() const noexcept { - return C.Val(); - } -}; + inline void Ref() noexcept { + C.Inc(); + } + + inline void UnRef() noexcept { + if (C.Val() == 1 || C.Dec() == 0) { + delete this; + } + } + + inline long RefCount() const noexcept { + return C.Val(); + } +}; template <class TStringType> class TBasicCharRef { @@ -109,27 +109,27 @@ public: using TChar = typename TStringType::TChar; TBasicCharRef(TStringType& s, size_t pos) - : S_(s) - , Pos_(pos) - { - } + : S_(s) + , Pos_(pos) + { + } operator TChar() const { return S_.at(Pos_); } - TChar* operator&() { + TChar* operator&() { return S_.begin() + Pos_; } - const TChar* operator&() const { + const TChar* operator&() const { return S_.cbegin() + Pos_; } TBasicCharRef& operator=(TChar c) { Y_ASSERT(Pos_ < S_.size() || (Pos_ == S_.size() && !c)); - S_.Detach()[Pos_] = c; + S_.Detach()[Pos_] = c; return *this; } @@ -160,13 +160,13 @@ class TBasicString: public TStringBase<TBasicString<TCharType, TTraits>, TCharTy public: // TODO: Move to private section using TBase = TStringBase<TBasicString, TCharType, TTraits>; - using TStringType = std::basic_string<TCharType, TTraits>; + using TStringType = std::basic_string<TCharType, TTraits>; #ifdef TSTRING_IS_STD_STRING - using TStorage = TStringType; + using TStorage = TStringType; using reference = typename TStorage::reference; #else - using TStdStr = TStdString<TStringType>; - using TStorage = TIntrusivePtr<TStdStr, TStringPtrOps<TStdStr>>; + using TStdStr = TStdString<TStringType>; + using TStorage = TIntrusivePtr<TStdStr, TStringPtrOps<TStdStr>>; using reference = TBasicCharRef<TBasicString>; #endif using char_type = TCharType; // TODO: DROP @@ -174,80 +174,80 @@ public: using traits_type = TTraits; using iterator = TCharType*; - using reverse_iterator = typename TBase::template TReverseIteratorBase<iterator>; + using reverse_iterator = typename TBase::template TReverseIteratorBase<iterator>; using typename TBase::const_iterator; - using typename TBase::const_reference; + using typename TBase::const_reference; using typename TBase::const_reverse_iterator; struct TUninitialized { - explicit TUninitialized(size_t size) - : Size(size) - { - } + explicit TUninitialized(size_t size) + : Size(size) + { + } size_t Size; }; static size_t max_size() noexcept { - static size_t res = TStringType().max_size(); - - return res; + static size_t res = TStringType().max_size(); + + return res; } protected: #ifdef TSTRING_IS_STD_STRING TStorage Storage_; #else - TStorage S_; + TStorage S_; + + template <typename... A> + static TStorage Construct(A&&... a) { + return {new TStdStr(std::forward<A>(a)...), typename TStorage::TNoIncrement()}; + } - template <typename... A> - static TStorage Construct(A&&... a) { - return {new TStdStr(std::forward<A>(a)...), typename TStorage::TNoIncrement()}; - } - static TStorage Construct() noexcept { - return TStdStr::NullStr(); - } - - TStdStr& StdStr() noexcept { - return *S_; - } - - const TStdStr& StdStr() const noexcept { - return *S_; - } - + return TStdStr::NullStr(); + } + + TStdStr& StdStr() noexcept { + return *S_; + } + + const TStdStr& StdStr() const noexcept { + return *S_; + } + /** * Makes a distinct copy of this string. `IsDetached()` is always true after this call. * * @throw std::length_error */ void Clone() { - Construct(StdStr()).Swap(S_); - } - - size_t RefCount() const noexcept { + Construct(StdStr()).Swap(S_); + } + + size_t RefCount() const noexcept { return S_.RefCount(); - } -#endif - -public: - inline const TStringType& ConstRef() const { -#ifdef TSTRING_IS_STD_STRING - return Storage_; -#else - return StdStr(); -#endif - } - - inline TStringType& MutRef() { -#ifdef TSTRING_IS_STD_STRING - return Storage_; -#else - Detach(); - - return StdStr(); -#endif + } +#endif + +public: + inline const TStringType& ConstRef() const { +#ifdef TSTRING_IS_STD_STRING + return Storage_; +#else + return StdStr(); +#endif + } + + inline TStringType& MutRef() { +#ifdef TSTRING_IS_STD_STRING + return Storage_; +#else + Detach(); + + return StdStr(); +#endif } inline const_reference operator[](size_t pos) const noexcept { @@ -277,7 +277,7 @@ public: if (Y_UNLIKELY(this->empty())) { return reference(*this, 0); } - + return reference(*this, length() - 1); #endif } @@ -286,7 +286,7 @@ public: inline reference front() noexcept { Y_ASSERT(!this->empty()); - + #ifdef TSTRING_IS_STD_STRING return Storage_.front(); #else @@ -295,64 +295,64 @@ public: } inline size_t length() const noexcept { - return ConstRef().length(); + return ConstRef().length(); } - + inline const TCharType* data() const noexcept { - return ConstRef().data(); - } - + return ConstRef().data(); + } + inline const TCharType* c_str() const noexcept { - return ConstRef().c_str(); + return ConstRef().c_str(); } // ~~~ STL compatible method to obtain data pointer ~~~ - iterator begin() { - return &*MutRef().begin(); + iterator begin() { + return &*MutRef().begin(); } - + iterator vend() { - return &*MutRef().end(); + return &*MutRef().end(); } reverse_iterator rbegin() { - return reverse_iterator(vend()); + return reverse_iterator(vend()); } reverse_iterator rend() { - return reverse_iterator(begin()); + return reverse_iterator(begin()); } - using TBase::begin; //!< const_iterator TStringBase::begin() const - using TBase::cbegin; //!< const_iterator TStringBase::cbegin() const - using TBase::cend; //!< const_iterator TStringBase::cend() const + using TBase::begin; //!< const_iterator TStringBase::begin() const + using TBase::cbegin; //!< const_iterator TStringBase::cbegin() const + using TBase::cend; //!< const_iterator TStringBase::cend() const using TBase::crbegin; //!< const_reverse_iterator TStringBase::crbegin() const using TBase::crend; //!< const_reverse_iterator TStringBase::crend() const - using TBase::end; //!< const_iterator TStringBase::end() const - using TBase::rbegin; //!< const_reverse_iterator TStringBase::rbegin() const + using TBase::end; //!< const_iterator TStringBase::end() const + using TBase::rbegin; //!< const_reverse_iterator TStringBase::rbegin() const using TBase::rend; //!< const_reverse_iterator TStringBase::rend() const inline size_t capacity() const noexcept { #ifdef TSTRING_IS_STD_STRING return Storage_.capacity(); #else - if (S_->IsNull()) { - return 0; - } - - return S_->capacity(); + if (S_->IsNull()) { + return 0; + } + + return S_->capacity(); #endif } - + TCharType* Detach() { #ifdef TSTRING_IS_STD_STRING return Storage_.data(); #else - if (Y_UNLIKELY(!IsDetached())) { - Clone(); + if (Y_UNLIKELY(!IsDetached())) { + Clone(); } - return (TCharType*)S_->data(); + return (TCharType*)S_->data(); #endif } @@ -360,13 +360,13 @@ public: #ifdef TSTRING_IS_STD_STRING return true; #else - return 1 == RefCount(); + return 1 == RefCount(); #endif } // ~~~ Size and capacity ~~~ TBasicString& resize(size_t n, TCharType c = ' ') { // remove or append - MutRef().resize(n, c); + MutRef().resize(n, c); return *this; } @@ -374,14 +374,14 @@ public: // ~~~ Constructor ~~~ : FAMILY0(,TBasicString) TBasicString() noexcept #ifndef TSTRING_IS_STD_STRING - : S_(Construct()) + : S_(Construct()) #endif - { + { } - + inline explicit TBasicString(::NDetail::TReserveTag rt) #ifndef TSTRING_IS_STD_STRING - : S_(Construct()) + : S_(Construct()) #endif { reserve(rt.Capacity); @@ -391,68 +391,68 @@ public: #ifdef TSTRING_IS_STD_STRING : Storage_(s.Storage_) #else - : S_(s.S_) + : S_(s.S_) #endif - { + { } - + inline TBasicString(TBasicString&& s) noexcept #ifdef TSTRING_IS_STD_STRING : Storage_(std::move(s.Storage_)) #else - : S_(Construct()) + : S_(Construct()) #endif { -#ifdef TSTRING_IS_STD_STRING -#else - s.swap(*this); +#ifdef TSTRING_IS_STD_STRING +#else + s.swap(*this); #endif } template <typename T, typename A> explicit inline TBasicString(const std::basic_string<TCharType, T, A>& s) - : TBasicString(s.data(), s.size()) - { - } - - template <typename T, typename A> - inline TBasicString(std::basic_string<TCharType, T, A>&& s) -#ifdef TSTRING_IS_STD_STRING - : Storage_(std::move(s)) -#else - : S_(s.empty() ? Construct() : Construct(std::move(s))) -#endif - { - } - - TBasicString(const TBasicString& s, size_t pos, size_t n) Y_NOEXCEPT + : TBasicString(s.data(), s.size()) + { + } + + template <typename T, typename A> + inline TBasicString(std::basic_string<TCharType, T, A>&& s) +#ifdef TSTRING_IS_STD_STRING + : Storage_(std::move(s)) +#else + : S_(s.empty() ? Construct() : Construct(std::move(s))) +#endif + { + } + + TBasicString(const TBasicString& s, size_t pos, size_t n) Y_NOEXCEPT #ifdef TSTRING_IS_STD_STRING : Storage_(s.Storage_, pos, n) -#else - : S_(n ? Construct(s, pos, n) : Construct()) +#else + : S_(n ? Construct(s, pos, n) : Construct()) #endif { } TBasicString(const TCharType* pc) - : TBasicString(pc, TBase::StrLen(pc)) + : TBasicString(pc, TBase::StrLen(pc)) { } // TODO thegeorg@: uncomment and fix clients // TBasicString(std::nullptr_t) = delete; - + TBasicString(const TCharType* pc, size_t n) #ifdef TSTRING_IS_STD_STRING : Storage_(pc, n) -#else - : S_(n ? Construct(pc, n) : Construct()) +#else + : S_(n ? Construct(pc, n) : Construct()) #endif { } TBasicString(std::nullptr_t, size_t) = delete; TBasicString(const TCharType* pc, size_t pos, size_t n) - : TBasicString(pc + pos, n) + : TBasicString(pc + pos, n) { } @@ -461,21 +461,21 @@ public: Storage_.push_back(c); } #else - explicit TBasicString(TExplicitType<TCharType> c) - : TBasicString(&c.Value(), 1) - { + explicit TBasicString(TExplicitType<TCharType> c) + : TBasicString(&c.Value(), 1) + { } - explicit TBasicString(const reference& c) - : TBasicString(&c, 1) - { + explicit TBasicString(const reference& c) + : TBasicString(&c, 1) + { } #endif TBasicString(size_t n, TCharType c) #ifdef TSTRING_IS_STD_STRING : Storage_(n, c) -#else - : S_(Construct(n, c)) +#else + : S_(Construct(n, c)) #endif { } @@ -487,25 +487,25 @@ public: * @throw std::length_error */ TBasicString(TUninitialized uninitialized) { -#if !defined(TSTRING_IS_STD_STRING) - S_ = Construct(); +#if !defined(TSTRING_IS_STD_STRING) + S_ = Construct(); #endif - ReserveAndResize(uninitialized.Size); + ReserveAndResize(uninitialized.Size); } TBasicString(const TCharType* b, const TCharType* e) - : TBasicString(b, e - b) + : TBasicString(b, e - b) { } explicit TBasicString(const TBasicStringBuf<TCharType, TTraits> s) - : TBasicString(s.data(), s.size()) + : TBasicString(s.data(), s.size()) { } template <typename Traits> explicit inline TBasicString(const std::basic_string_view<TCharType, Traits>& s) - : TBasicString(s.data(), s.size()) + : TBasicString(s.data(), s.size()) { } @@ -531,11 +531,11 @@ public: } private: - template <typename... R> + template <typename... R> static size_t SumLength(const TBasicStringBuf<TCharType, TTraits> s1, const R&... r) noexcept { return s1.size() + SumLength(r...); } - + template <typename... R> static size_t SumLength(const TCharType /*s1*/, const R&... r) noexcept { return 1 + SumLength(r...); @@ -545,7 +545,7 @@ private: return 0; } - template <typename... R> + template <typename... R> static void CopyAll(TCharType* p, const TBasicStringBuf<TCharType, TTraits> s, const R&... r) { TTraits::copy(p, s.data(), s.size()); CopyAll(p + s.size(), r...); @@ -566,24 +566,24 @@ public: Storage_.clear(); #else if (IsDetached()) { - S_->clear(); - - return; - } - - Construct().Swap(S_); + S_->clear(); + + return; + } + + Construct().Swap(S_); #endif } template <typename... R> static inline TBasicString Join(const R&... r) { - TBasicString s{TUninitialized{SumLength(r...)}}; - - TBasicString::CopyAll((TCharType*)s.data(), r...); - + TBasicString s{TUninitialized{SumLength(r...)}}; + + TBasicString::CopyAll((TCharType*)s.data(), r...); + return s; - } - + } + // ~~~ Assignment ~~~ : FAMILY0(TBasicString&, assign); TBasicString& assign(size_t size, TCharType ch) { ReserveAndResize(size); @@ -593,59 +593,59 @@ public: TBasicString& assign(const TBasicString& s) { TBasicString(s).swap(*this); - + return *this; } - + TBasicString& assign(const TBasicString& s, size_t pos, size_t n) { return assign(TBasicString(s, pos, n)); } - + TBasicString& assign(const TCharType* pc) { - return assign(pc, TBase::StrLen(pc)); + return assign(pc, TBase::StrLen(pc)); } - + TBasicString& assign(TCharType ch) { return assign(&ch, 1); } TBasicString& assign(const TCharType* pc, size_t len) { -#if defined(address_sanitizer_enabled) || defined(thread_sanitizer_enabled) - pc = (const TCharType*)HidePointerOrigin((void*)pc); -#endif - if (IsDetached()) { - MutRef().assign(pc, len); - } else { - TBasicString(pc, len).swap(*this); - } - +#if defined(address_sanitizer_enabled) || defined(thread_sanitizer_enabled) + pc = (const TCharType*)HidePointerOrigin((void*)pc); +#endif + if (IsDetached()) { + MutRef().assign(pc, len); + } else { + TBasicString(pc, len).swap(*this); + } + return *this; } - + TBasicString& assign(const TCharType* first, const TCharType* last) { return assign(first, last - first); - } - + } + TBasicString& assign(const TCharType* pc, size_t pos, size_t n) { return assign(pc + pos, n); } - - TBasicString& assign(const TBasicStringBuf<TCharType, TTraits> s) { - return assign(s.data(), s.size()); - } - - TBasicString& assign(const TBasicStringBuf<TCharType, TTraits> s, size_t spos, size_t sn = TBase::npos) { - return assign(s.SubString(spos, sn)); - } - - inline TBasicString& AssignNoAlias(const TCharType* pc, size_t len) { - return assign(pc, len); - } - - inline TBasicString& AssignNoAlias(const TCharType* b, const TCharType* e) { - return AssignNoAlias(b, e - b); - } - + + TBasicString& assign(const TBasicStringBuf<TCharType, TTraits> s) { + return assign(s.data(), s.size()); + } + + TBasicString& assign(const TBasicStringBuf<TCharType, TTraits> s, size_t spos, size_t sn = TBase::npos) { + return assign(s.SubString(spos, sn)); + } + + inline TBasicString& AssignNoAlias(const TCharType* pc, size_t len) { + return assign(pc, len); + } + + inline TBasicString& AssignNoAlias(const TCharType* b, const TCharType* e) { + return AssignNoAlias(b, e - b); + } + TBasicString& AssignNoAlias(const TBasicStringBuf<TCharType, TTraits> s) { return AssignNoAlias(s.data(), s.size()); } @@ -683,13 +683,13 @@ public: return *this; } - template <typename T, typename A> - TBasicString& operator=(std::basic_string<TCharType, T, A>&& s) noexcept { - TBasicString(std::move(s)).swap(*this); - - return *this; - } - + template <typename T, typename A> + TBasicString& operator=(std::basic_string<TCharType, T, A>&& s) noexcept { + TBasicString(std::move(s)).swap(*this); + + return *this; + } + TBasicString& operator=(const TBasicStringBuf<TCharType, TTraits> s) { return assign(s); } @@ -707,68 +707,68 @@ public: return assign(ch); } - inline void reserve(size_t len) { - MutRef().reserve(len); - } - + inline void reserve(size_t len) { + MutRef().reserve(len); + } + // ~~~ Appending ~~~ : FAMILY0(TBasicString&, append); inline TBasicString& append(size_t count, TCharType ch) { - MutRef().append(count, ch); - + MutRef().append(count, ch); + return *this; - } - + } + inline TBasicString& append(const TBasicString& s) { - MutRef().append(s.ConstRef()); + MutRef().append(s.ConstRef()); return *this; } - + inline TBasicString& append(const TBasicString& s, size_t pos, size_t n) { - MutRef().append(s.ConstRef(), pos, n); + MutRef().append(s.ConstRef(), pos, n); return *this; } - - inline TBasicString& append(const TCharType* pc) Y_NOEXCEPT { - MutRef().append(pc); + + inline TBasicString& append(const TCharType* pc) Y_NOEXCEPT { + MutRef().append(pc); return *this; } - + inline TBasicString& append(TCharType c) { - MutRef().push_back(c); - + MutRef().push_back(c); + return *this; - } - + } + inline TBasicString& append(const TCharType* first, const TCharType* last) { - MutRef().append(first, last); + MutRef().append(first, last); return *this; - } - + } + inline TBasicString& append(const TCharType* pc, size_t len) { - MutRef().append(pc, len); + MutRef().append(pc, len); return *this; - } - - inline void ReserveAndResize(size_t len) { - ::ResizeUninitialized(MutRef(), len); - } - - TBasicString& AppendNoAlias(const TCharType* pc, size_t len) { - if (len) { - auto s = this->size(); - - ReserveAndResize(s + len); - memcpy(&*(begin() + s), pc, len * sizeof(*pc)); - } - + } + + inline void ReserveAndResize(size_t len) { + ::ResizeUninitialized(MutRef(), len); + } + + TBasicString& AppendNoAlias(const TCharType* pc, size_t len) { + if (len) { + auto s = this->size(); + + ReserveAndResize(s + len); + memcpy(&*(begin() + s), pc, len * sizeof(*pc)); + } + return *this; - } - + } + TBasicString& AppendNoAlias(const TBasicStringBuf<TCharType, TTraits> s) { return AppendNoAlias(s.data(), s.size()); } @@ -785,10 +785,10 @@ public: return append(s.SubString(spos, sn)); } - TBasicString& append(const TCharType* pc, size_t pos, size_t n, size_t pc_len = TBase::npos) { + TBasicString& append(const TCharType* pc, size_t pos, size_t n, size_t pc_len = TBase::npos) { return append(pc + pos, Min(n, pc_len - pos)); } - + /** * WARN: * Certain invocations of this method will result in link-time error. @@ -801,47 +801,47 @@ public: TBasicString& AppendUtf16(const ::TWtringBuf& s); inline void push_back(TCharType c) { - // TODO + // TODO append(c); } - template <class T> + template <class T> TBasicString& operator+=(const T& s) { - return append(s); + return append(s); } - + template <class T> friend TBasicString operator*(const TBasicString& s, T count) { TBasicString result; - - for (T i = 0; i < count; ++i) { + + for (T i = 0; i < count; ++i) { result += s; - } - + } + return result; } template <class T> TBasicString& operator*=(T count) { TBasicString temp; - - for (T i = 0; i < count; ++i) { + + for (T i = 0; i < count; ++i) { temp += *this; - } - + } + swap(temp); - + return *this; } - - operator const TStringType&() const noexcept { - return this->ConstRef(); + + operator const TStringType&() const noexcept { + return this->ConstRef(); + } + + operator TStringType&() { + return this->MutRef(); } - operator TStringType&() { - return this->MutRef(); - } - /* * Following overloads of "operator+" aim to choose the cheapest implementation depending on * summand types: lvalues, detached rvalues, shared rvalues. @@ -867,14 +867,14 @@ public: s1 += s2; return std::move(s1); } - + friend TBasicString operator+(const TBasicString& s1, TBasicString&& s2) Y_WARN_UNUSED_RESULT { s2.prepend(s1); return std::move(s2); } friend TBasicString operator+(TBasicString&& s1, TBasicString&& s2) Y_WARN_UNUSED_RESULT { -#if 0 && !defined(TSTRING_IS_STD_STRING) +#if 0 && !defined(TSTRING_IS_STD_STRING) if (!s1.IsDetached() && s2.IsDetached()) { s2.prepend(s1); return std::move(s2); @@ -888,7 +888,7 @@ public: s1 += s2; return std::move(s1); } - + friend TBasicString operator+(TBasicString&& s1, const TCharType* s2) Y_WARN_UNUSED_RESULT { s1 += s2; return std::move(s1); @@ -899,7 +899,7 @@ public: return std::move(s1); } - friend TBasicString operator+(TExplicitType<TCharType> ch, const TBasicString& s) Y_WARN_UNUSED_RESULT { + friend TBasicString operator+(TExplicitType<TCharType> ch, const TBasicString& s) Y_WARN_UNUSED_RESULT { return Join(TCharType(ch), s); } @@ -937,41 +937,41 @@ public: return Join(s1, s2); } - friend TBasicString operator+(std::basic_string<TCharType, TTraits> l, TBasicString r) { - return l + r.ConstRef(); - } - - friend TBasicString operator+(TBasicString l, std::basic_string<TCharType, TTraits> r) { - return l.ConstRef() + r; - } - + friend TBasicString operator+(std::basic_string<TCharType, TTraits> l, TBasicString r) { + return l + r.ConstRef(); + } + + friend TBasicString operator+(TBasicString l, std::basic_string<TCharType, TTraits> r) { + return l.ConstRef() + r; + } + // ~~~ Prepending ~~~ : FAMILY0(TBasicString&, prepend); TBasicString& prepend(const TBasicString& s) { - MutRef().insert(0, s.ConstRef()); + MutRef().insert(0, s.ConstRef()); return *this; } - + TBasicString& prepend(const TBasicString& s, size_t pos, size_t n) { - MutRef().insert(0, s.ConstRef(), pos, n); + MutRef().insert(0, s.ConstRef(), pos, n); return *this; } - + TBasicString& prepend(const TCharType* pc) { - MutRef().insert(0, pc); + MutRef().insert(0, pc); return *this; } - + TBasicString& prepend(size_t n, TCharType c) { - MutRef().insert(size_t(0), n, c); + MutRef().insert(size_t(0), n, c); return *this; } TBasicString& prepend(TCharType c) { - MutRef().insert(size_t(0), 1, c); + MutRef().insert(size_t(0), 1, c); return *this; } @@ -982,29 +982,29 @@ public: // ~~~ Insertion ~~~ : FAMILY1(TBasicString&, insert, size_t pos); TBasicString& insert(size_t pos, const TBasicString& s) { - MutRef().insert(pos, s.ConstRef()); + MutRef().insert(pos, s.ConstRef()); return *this; } - + TBasicString& insert(size_t pos, const TBasicString& s, size_t pos1, size_t n1) { - MutRef().insert(pos, s.ConstRef(), pos1, n1); + MutRef().insert(pos, s.ConstRef(), pos1, n1); return *this; } - + TBasicString& insert(size_t pos, const TCharType* pc) { - MutRef().insert(pos, pc); + MutRef().insert(pos, pc); return *this; } - + TBasicString& insert(size_t pos, const TCharType* pc, size_t len) { - MutRef().insert(pos, pc, len); + MutRef().insert(pos, pc, len); return *this; - } - + } + TBasicString& insert(const_iterator pos, const_iterator b, const_iterator e) { #ifdef TSTRING_IS_STD_STRING Storage_.insert(Storage_.begin() + this->off(pos), b, e); @@ -1013,106 +1013,106 @@ public: #else return insert(this->off(pos), b, e - b); #endif - } - + } + TBasicString& insert(size_t pos, size_t n, TCharType c) { - MutRef().insert(pos, n, c); + MutRef().insert(pos, n, c); return *this; - } - + } + TBasicString& insert(const_iterator pos, size_t len, TCharType ch) { return this->insert(this->off(pos), len, ch); - } - + } + TBasicString& insert(const_iterator pos, TCharType ch) { return this->insert(pos, 1, ch); - } - + } + TBasicString& insert(size_t pos, const TBasicStringBuf<TCharType, TTraits> s, size_t spos = 0, size_t sn = TBase::npos) { - MutRef().insert(pos, s, spos, sn); + MutRef().insert(pos, s, spos, sn); return *this; } // ~~~ Removing ~~~ - TBasicString& remove(size_t pos, size_t n) Y_NOEXCEPT { - if (pos < length()) { - MutRef().erase(pos, n); - } + TBasicString& remove(size_t pos, size_t n) Y_NOEXCEPT { + if (pos < length()) { + MutRef().erase(pos, n); + } return *this; } - - TBasicString& remove(size_t pos = 0) Y_NOEXCEPT { + + TBasicString& remove(size_t pos = 0) Y_NOEXCEPT { if (pos < length()) { - MutRef().erase(pos); + MutRef().erase(pos); } - + return *this; } - TBasicString& erase(size_t pos = 0, size_t n = TBase::npos) Y_NOEXCEPT { - MutRef().erase(pos, n); + TBasicString& erase(size_t pos = 0, size_t n = TBase::npos) Y_NOEXCEPT { + MutRef().erase(pos, n); return *this; } - - TBasicString& erase(const_iterator b, const_iterator e) Y_NOEXCEPT { - return erase(this->off(b), e - b); - } - - TBasicString& erase(const_iterator i) Y_NOEXCEPT { - return erase(i, i + 1); - } - - TBasicString& pop_back() Y_NOEXCEPT { + + TBasicString& erase(const_iterator b, const_iterator e) Y_NOEXCEPT { + return erase(this->off(b), e - b); + } + + TBasicString& erase(const_iterator i) Y_NOEXCEPT { + return erase(i, i + 1); + } + + TBasicString& pop_back() Y_NOEXCEPT { Y_ASSERT(!this->empty()); - MutRef().pop_back(); - + MutRef().pop_back(); + return *this; - } - + } + // ~~~ replacement ~~~ : FAMILY2(TBasicString&, replace, size_t pos, size_t n); - TBasicString& replace(size_t pos, size_t n, const TBasicString& s) Y_NOEXCEPT { - MutRef().replace(pos, n, s.ConstRef()); - - return *this; + TBasicString& replace(size_t pos, size_t n, const TBasicString& s) Y_NOEXCEPT { + MutRef().replace(pos, n, s.ConstRef()); + + return *this; } - - TBasicString& replace(size_t pos, size_t n, const TBasicString& s, size_t pos1, size_t n1) Y_NOEXCEPT { - MutRef().replace(pos, n, s.ConstRef(), pos1, n1); - - return *this; + + TBasicString& replace(size_t pos, size_t n, const TBasicString& s, size_t pos1, size_t n1) Y_NOEXCEPT { + MutRef().replace(pos, n, s.ConstRef(), pos1, n1); + + return *this; } - - TBasicString& replace(size_t pos, size_t n, const TCharType* pc) Y_NOEXCEPT { - MutRef().replace(pos, n, pc); - - return *this; + + TBasicString& replace(size_t pos, size_t n, const TCharType* pc) Y_NOEXCEPT { + MutRef().replace(pos, n, pc); + + return *this; } - TBasicString& replace(size_t pos, size_t n, const TCharType* s, size_t len) Y_NOEXCEPT { - MutRef().replace(pos, n, s, len); - - return *this; + TBasicString& replace(size_t pos, size_t n, const TCharType* s, size_t len) Y_NOEXCEPT { + MutRef().replace(pos, n, s, len); + + return *this; } - TBasicString& replace(size_t pos, size_t n, const TCharType* s, size_t spos, size_t sn) Y_NOEXCEPT { - MutRef().replace(pos, n, s + spos, sn - spos); - - return *this; + TBasicString& replace(size_t pos, size_t n, const TCharType* s, size_t spos, size_t sn) Y_NOEXCEPT { + MutRef().replace(pos, n, s + spos, sn - spos); + + return *this; } - TBasicString& replace(size_t pos, size_t n1, size_t n2, TCharType c) Y_NOEXCEPT { - MutRef().replace(pos, n1, n2, c); - - return *this; + TBasicString& replace(size_t pos, size_t n1, size_t n2, TCharType c) Y_NOEXCEPT { + MutRef().replace(pos, n1, n2, c); + + return *this; } - TBasicString& replace(size_t pos, size_t n, const TBasicStringBuf<TCharType, TTraits> s, size_t spos = 0, size_t sn = TBase::npos) Y_NOEXCEPT { - MutRef().replace(pos, n, s, spos, sn); + TBasicString& replace(size_t pos, size_t n, const TBasicStringBuf<TCharType, TTraits> s, size_t spos = 0, size_t sn = TBase::npos) Y_NOEXCEPT { + MutRef().replace(pos, n, s, spos, sn); return *this; } @@ -1121,7 +1121,7 @@ public: #ifdef TSTRING_IS_STD_STRING std::swap(Storage_, s.Storage_); #else - S_.Swap(s.S_); + S_.Swap(s.S_); #endif } @@ -1175,14 +1175,14 @@ public: Storage_[i] = c; } #else - auto c = f(i, data()[i]); - if (c != data()[i]) { + auto c = f(i, data()[i]); + if (c != data()[i]) { if (!changed) { Detach(); changed = true; } - begin()[i] = c; + begin()[i] = c; } #endif } @@ -1194,21 +1194,21 @@ public: std::ostream& operator<<(std::ostream&, const TString&); std::istream& operator>>(std::istream&, TString&); -template <typename TCharType, typename TTraits> +template <typename TCharType, typename TTraits> TBasicString<TCharType> to_lower(const TBasicString<TCharType, TTraits>& s) { TBasicString<TCharType> ret(s); ret.to_lower(); return ret; } -template <typename TCharType, typename TTraits> +template <typename TCharType, typename TTraits> TBasicString<TCharType> to_upper(const TBasicString<TCharType, TTraits>& s) { TBasicString<TCharType> ret(s); ret.to_upper(); return ret; } -template <typename TCharType, typename TTraits> +template <typename TCharType, typename TTraits> TBasicString<TCharType> to_title(const TBasicString<TCharType, TTraits>& s) { TBasicString<TCharType> ret(s); ret.to_title(); @@ -1216,7 +1216,7 @@ TBasicString<TCharType> to_title(const TBasicString<TCharType, TTraits>& s) { } namespace std { - template <> + template <> struct hash<TString> { using argument_type = TString; using result_type = size_t; @@ -1224,64 +1224,64 @@ namespace std { return NHashPrivate::ComputeStringHash(s.data(), s.size()); } }; -} - -#undef Y_NOEXCEPT - -template <class S> -inline S LegacySubstr(const S& s, size_t pos, size_t n = S::npos) { - size_t len = s.length(); - - pos = Min(pos, len); - n = Min(n, len - pos); - - return S(s, pos, n); -} - -template <typename S, typename... Args> -inline S&& LegacyReplace(S&& s, size_t pos, Args&&... args) { - if (pos <= s.length()) { - s.replace(pos, std::forward<Args>(args)...); - } - - return s; -} - -template <typename S, typename... Args> -inline S&& LegacyErase(S&& s, size_t pos, Args&&... args) { - if (pos <= s.length()) { - s.erase(pos, std::forward<Args>(args)...); - } - - return s; -} - -inline const char* LegacyStr(const char* s) noexcept { - return s ? s : ""; -} - -// interop -template <class TCharType, class TTraits> -auto& MutRef(TBasicString<TCharType, TTraits>& s) { - return s.MutRef(); -} - -template <class TCharType, class TTraits> -const auto& ConstRef(const TBasicString<TCharType, TTraits>& s) noexcept { - return s.ConstRef(); -} - -template <class TCharType, class TCharTraits, class TAllocator> -auto& MutRef(std::basic_string<TCharType, TCharTraits, TAllocator>& s) noexcept { - return s; -} - -template <class TCharType, class TCharTraits, class TAllocator> -const auto& ConstRef(const std::basic_string<TCharType, TCharTraits, TAllocator>& s) noexcept { - return s; -} - -template <class TCharType, class TTraits> -void ResizeUninitialized(TBasicString<TCharType, TTraits>& s, size_t len) { - s.ReserveAndResize(len); -} +} + +#undef Y_NOEXCEPT + +template <class S> +inline S LegacySubstr(const S& s, size_t pos, size_t n = S::npos) { + size_t len = s.length(); + + pos = Min(pos, len); + n = Min(n, len - pos); + + return S(s, pos, n); +} + +template <typename S, typename... Args> +inline S&& LegacyReplace(S&& s, size_t pos, Args&&... args) { + if (pos <= s.length()) { + s.replace(pos, std::forward<Args>(args)...); + } + + return s; +} + +template <typename S, typename... Args> +inline S&& LegacyErase(S&& s, size_t pos, Args&&... args) { + if (pos <= s.length()) { + s.erase(pos, std::forward<Args>(args)...); + } + + return s; +} + +inline const char* LegacyStr(const char* s) noexcept { + return s ? s : ""; +} + +// interop +template <class TCharType, class TTraits> +auto& MutRef(TBasicString<TCharType, TTraits>& s) { + return s.MutRef(); +} + +template <class TCharType, class TTraits> +const auto& ConstRef(const TBasicString<TCharType, TTraits>& s) noexcept { + return s.ConstRef(); +} + +template <class TCharType, class TCharTraits, class TAllocator> +auto& MutRef(std::basic_string<TCharType, TCharTraits, TAllocator>& s) noexcept { + return s; +} + +template <class TCharType, class TCharTraits, class TAllocator> +const auto& ConstRef(const std::basic_string<TCharType, TCharTraits, TAllocator>& s) noexcept { + return s; +} + +template <class TCharType, class TTraits> +void ResizeUninitialized(TBasicString<TCharType, TTraits>& s, size_t len) { + s.ReserveAndResize(len); +} diff --git a/util/generic/string.pxd b/util/generic/string.pxd index 0f3fb1c7fe..c25f7392a1 100644 --- a/util/generic/string.pxd +++ b/util/generic/string.pxd @@ -1,5 +1,5 @@ from libcpp.string cimport string as _std_string - + cdef extern from "<util/generic/strbuf.h>" nogil: cdef cppclass TStringBuf: @@ -13,9 +13,9 @@ cdef extern from "<util/generic/strbuf.h>" nogil: cdef extern from "<util/generic/string.h>" nogil: - + size_t npos "TString::npos" - + # Inheritance is bogus, but it's safe to assume TString is-a TStringBuf via implicit cast cdef cppclass TString(TStringBuf): TString() except + @@ -31,88 +31,88 @@ cdef extern from "<util/generic/string.h>" nogil: TString(TStringBuf&) except + TString(TStringBuf&, TStringBuf&) except + TString(TStringBuf&, TStringBuf&, TStringBuf&) except + - - const char* c_str() - size_t max_size() - size_t length() + + const char* c_str() + size_t max_size() + size_t length() void resize(size_t) except + void resize(size_t, char c) except + - size_t capacity() + size_t capacity() void reserve(size_t) except + void clear() except + - bint empty() - - char& at(size_t) - char& operator[](size_t) + bint empty() + + char& at(size_t) + char& operator[](size_t) int compare(TStringBuf&) - + TString& append(TStringBuf&) except + TString& append(TStringBuf&, size_t, size_t) except + TString& append(char *) except + TString& append(char *, size_t) except + TString& append(size_t, char) except + - + void push_back(char c) except + - + TString& assign(TStringBuf&) except + TString& assign(TStringBuf&, size_t, size_t) except + TString& assign(char *) except + TString& assign(char *, size_t) except + - + TString& insert(size_t, TString&) except + TString& insert(size_t, TString&, size_t, size_t) except + TString& insert(size_t, char* s) except + TString& insert(size_t, char* s, size_t) except + TString& insert(size_t, size_t, char c) except + - + size_t copy(char *, size_t) except + size_t copy(char *, size_t, size_t) except + - + size_t find(TStringBuf&) size_t find(TStringBuf&, size_t pos) size_t find(char) - size_t find(char, size_t pos) - + size_t find(char, size_t pos) + size_t rfind(TStringBuf&) size_t rfind(TStringBuf&, size_t pos) size_t rfind(char) size_t rfind(char, size_t pos) - - size_t find_first_of(char c) + + size_t find_first_of(char c) size_t find_first_of(char c, size_t pos) size_t find_first_of(TStringBuf& set) size_t find_first_of(TStringBuf& set, size_t pos) - - size_t find_first_not_of(char c) + + size_t find_first_not_of(char c) size_t find_first_not_of(char c, size_t pos) size_t find_first_not_of(TStringBuf& set) size_t find_first_not_of(TStringBuf& set, size_t pos) - - size_t find_last_of(char c) + + size_t find_last_of(char c) size_t find_last_of(char c, size_t pos) size_t find_last_of(TStringBuf& set) size_t find_last_of(TStringBuf& set, size_t pos) - + TString substr(size_t pos) except + TString substr(size_t pos, size_t n) except + - + TString operator+(TStringBuf& rhs) except + TString operator+(char* rhs) except + - + bint operator==(TStringBuf&) - bint operator==(char*) - + bint operator==(char*) + bint operator!=(TStringBuf&) bint operator!=(char*) - + bint operator<(TStringBuf&) bint operator<(char*) - + bint operator>(TStringBuf&) bint operator>(char*) - + bint operator<=(TStringBuf&) bint operator<=(char*) - + bint operator>=(TStringBuf&) bint operator>=(char*) diff --git a/util/generic/string_hash.h b/util/generic/string_hash.h index a272ef4340..b949c7a2d9 100644 --- a/util/generic/string_hash.h +++ b/util/generic/string_hash.h @@ -13,9 +13,9 @@ namespace NHashPrivate { template <typename C> size_t ComputeStringHash(const C* ptr, size_t size) noexcept { #if defined(_64_) && !defined(NO_CITYHASH) - return CityHash64((const char*)ptr, size * sizeof(C)); + return CityHash64((const char*)ptr, size * sizeof(C)); #else - return MurmurHashSizeT((const char*)ptr, size * sizeof(C)); + return MurmurHashSizeT((const char*)ptr, size * sizeof(C)); #endif } } diff --git a/util/generic/string_transparent_hash_ut.cpp b/util/generic/string_transparent_hash_ut.cpp index 1b9791d621..b87fa2843e 100644 --- a/util/generic/string_transparent_hash_ut.cpp +++ b/util/generic/string_transparent_hash_ut.cpp @@ -1,7 +1,7 @@ #include "string.h" -#include "vector.h" +#include "vector.h" #include "strbuf.h" - + #include <library/cpp/testing/unittest/registar.h> #include <library/cpp/containers/absl_flat_hash/flat_hash_set.h> @@ -16,4 +16,4 @@ Y_UNIT_TEST_SUITE(StringHashFunctorTests) { UNIT_ASSERT_UNEQUAL(s.find(TStringBuf("foo")), s.end()); UNIT_ASSERT_EQUAL(s.find(TStringBuf("bar")), s.end()); } -} +} diff --git a/util/generic/string_ut.cpp b/util/generic/string_ut.cpp index 19c4c84278..ac82e9091d 100644 --- a/util/generic/string_ut.cpp +++ b/util/generic/string_ut.cpp @@ -1,32 +1,32 @@ -#include "deque.h" +#include "deque.h" #include "strbuf.h" #include "string_ut.h" -#include "vector.h" -#include "yexception.h" - +#include "vector.h" +#include "yexception.h" + #include <util/charset/wide.h> #include <util/str_stl.h> #include <util/stream/output.h> #include <util/string/subst.h> -#include <string> -#include <sstream> -#include <algorithm> -#include <stdexcept> - +#include <string> +#include <sstream> +#include <algorithm> +#include <stdexcept> + #ifdef TSTRING_IS_STD_STRING static_assert(sizeof(TString) == sizeof(std::string), "expect sizeof(TString) == sizeof(std::string)"); #else static_assert(sizeof(TString) == sizeof(const char*), "expect sizeof(TString) == sizeof(const char*)"); #endif -class TStringTestZero: public TTestBase { +class TStringTestZero: public TTestBase { UNIT_TEST_SUITE(TStringTestZero); - UNIT_TEST(TestZero); + UNIT_TEST(TestZero); UNIT_TEST_SUITE_END(); - + public: - void TestZero() { + void TestZero() { const char data[] = "abc\0def\0"; TString s(data, sizeof(data)); UNIT_ASSERT(s.size() == sizeof(data)); @@ -34,19 +34,19 @@ public: UNIT_ASSERT(s.EndsWith(s)); UNIT_ASSERT(s.Contains('\0')); - const char raw_def[] = "def"; - const char raw_zero[] = "\0"; + const char raw_def[] = "def"; + const char raw_zero[] = "\0"; TString def(raw_def, sizeof(raw_def) - 1); TString zero(raw_zero, sizeof(raw_zero) - 1); - UNIT_ASSERT_EQUAL(4, s.find(raw_def)); - UNIT_ASSERT_EQUAL(4, s.find(def)); - UNIT_ASSERT_EQUAL(4, s.find_first_of(raw_def)); - UNIT_ASSERT_EQUAL(3, s.find_first_of(zero)); - UNIT_ASSERT_EQUAL(7, s.find_first_not_of(def, 4)); - - const char nonSubstring[] = "def\0ghi"; + UNIT_ASSERT_EQUAL(4, s.find(raw_def)); + UNIT_ASSERT_EQUAL(4, s.find(def)); + UNIT_ASSERT_EQUAL(4, s.find_first_of(raw_def)); + UNIT_ASSERT_EQUAL(3, s.find_first_of(zero)); + UNIT_ASSERT_EQUAL(7, s.find_first_not_of(def, 4)); + + const char nonSubstring[] = "def\0ghi"; UNIT_ASSERT_EQUAL(TString::npos, s.find(TString(nonSubstring, sizeof(nonSubstring)))); - + TString copy = s; copy.replace(copy.size() - 1, 1, "z"); UNIT_ASSERT(s != copy); @@ -88,10 +88,10 @@ protected: //Expected exception is length_error: UNIT_ASSERT(false); } - } - + } + void reserve() { -#if 0 +#if 0 TStringType s; // @todo use UNIT_TEST_EXCEPTION try { @@ -148,152 +148,152 @@ protected: UNIT_ASSERT(s.IsDetached()); #endif #endif - } - + } + void short_string() { TStringType const ref_short_str1(Data_.str1()), ref_short_str2(Data_.str2()); TStringType short_str1(ref_short_str1), short_str2(ref_short_str2); TStringType const ref_long_str1(Data_.str__________________________________________________1()); TStringType const ref_long_str2(Data_.str__________________________________________________2()); TStringType long_str1(ref_long_str1), long_str2(ref_long_str2); - + UNIT_ASSERT(short_str1 == ref_short_str1); UNIT_ASSERT(long_str1 == ref_long_str1); - + { TStringType str1(short_str1); str1 = long_str1; UNIT_ASSERT(str1 == ref_long_str1); } - + { TStringType str1(long_str1); str1 = short_str1; UNIT_ASSERT(str1 == ref_short_str1); } - + { short_str1.swap(short_str2); UNIT_ASSERT((short_str1 == ref_short_str2) && (short_str2 == ref_short_str1)); short_str1.swap(short_str2); } - + { long_str1.swap(long_str2); UNIT_ASSERT((long_str1 == ref_long_str2) && (long_str2 == ref_long_str1)); long_str1.swap(long_str2); } - + { short_str1.swap(long_str1); UNIT_ASSERT((short_str1 == ref_long_str1) && (long_str1 == ref_short_str1)); short_str1.swap(long_str1); } - + { long_str1.swap(short_str1); UNIT_ASSERT((short_str1 == ref_long_str1) && (long_str1 == ref_short_str1)); long_str1.swap(short_str1); } - + { //This is to test move constructor TVector<TStringType> str_vect; - + str_vect.push_back(short_str1); str_vect.push_back(long_str1); str_vect.push_back(short_str2); str_vect.push_back(long_str2); - - UNIT_ASSERT(str_vect[0] == ref_short_str1); - UNIT_ASSERT(str_vect[1] == ref_long_str1); - UNIT_ASSERT(str_vect[2] == ref_short_str2); - UNIT_ASSERT(str_vect[3] == ref_long_str2); + + UNIT_ASSERT(str_vect[0] == ref_short_str1); + UNIT_ASSERT(str_vect[1] == ref_long_str1); + UNIT_ASSERT(str_vect[2] == ref_short_str2); + UNIT_ASSERT(str_vect[3] == ref_long_str2); } - } - + } + void erase() { TChar const* c_str = Data_.Hello_World(); TStringType str(c_str); UNIT_ASSERT(str == c_str); - + str.erase(str.begin() + 1, str.end() - 1); // Erase all but first and last. - + size_t i; for (i = 0; i < str.size(); ++i) { switch (i) { case 0: UNIT_ASSERT(str[i] == *Data_.H()); break; - + case 1: UNIT_ASSERT(str[i] == *Data_.d()); break; - + default: UNIT_ASSERT(false); } - } - + } + str.insert(1, c_str); - str.erase(str.begin()); // Erase first element. + str.erase(str.begin()); // Erase first element. str.erase(str.end() - 1); // Erase last element. UNIT_ASSERT(str == c_str); str.clear(); // Erase all. UNIT_ASSERT(str.empty()); - + str = c_str; UNIT_ASSERT(str == c_str); - + str.erase(1, str.size() - 1); // Erase all but first and last. for (i = 0; i < str.size(); i++) { switch (i) { case 0: UNIT_ASSERT(str[i] == *Data_.H()); break; - + case 1: UNIT_ASSERT(str[i] == *Data_.d()); break; - + default: UNIT_ASSERT(false); } - } + } str.erase(1); UNIT_ASSERT(str == Data_.H()); - } - + } + void data() { TStringType xx; - + // ISO-IEC-14882:1998(E), 21.3.6, paragraph 3 UNIT_ASSERT(xx.data() != nullptr); } - + void c_str() { TStringType low(Data_._2004_01_01()); TStringType xx; TStringType yy; - + // ISO-IEC-14882:1998(E), 21.3.6, paragraph 1 UNIT_ASSERT(*(yy.c_str()) == 0); - + // Blocks A and B should follow each other. // Block A: xx = Data_._123456(); xx += low; UNIT_ASSERT(xx.c_str() == TView(Data_._1234562004_01_01())); // End of block A - + // Block B: xx = Data_._1234(); xx += Data_._5(); UNIT_ASSERT(xx.c_str() == TView(Data_._12345())); // End of block B } - + void null_char_of_empty() { const TStringType s; @@ -303,10 +303,10 @@ protected: void null_char() { // ISO/IEC 14882:1998(E), ISO/IEC 14882:2003(E), 21.3.4 ('... the const version') const TStringType s(Data_._123456()); - + UNIT_ASSERT(s[s.size()] == 0); } - + // Allowed since C++17, see http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2475 void null_char_assignment_to_subscript_of_empty() { TStringType s; @@ -320,7 +320,7 @@ protected: trailing_zero = 0; UNIT_ASSERT(trailing_zero == 0); } - + // Allowed since C++17, see http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#2475 void null_char_assignment_to_subscript_of_nonempty() { TStringType s(Data_._123456()); @@ -358,122 +358,122 @@ protected: void insert() { TStringType strorg = Data_.This_is_test_string_for_string_calls(); TStringType str; - + // In case of reallocation there is no auto reference problem // so we reserve a big enough TStringType to be sure to test this // particular point. - + str.reserve(100); str = strorg; - + //test self insertion: str.insert(10, str.c_str() + 5, 15); UNIT_ASSERT(str == Data_.This_is_teis_test_string_st_string_for_string_calls()); - + str = strorg; str.insert(15, str.c_str() + 5, 25); UNIT_ASSERT(str == Data_.This_is_test_stis_test_string_for_stringring_for_string_calls()); - + str = strorg; str.insert(0, str.c_str() + str.size() - 4, 4); UNIT_ASSERT(str == Data_.allsThis_is_test_string_for_string_calls()); - + str = strorg; str.insert(0, str.c_str() + str.size() / 2 - 1, str.size() / 2 + 1); UNIT_ASSERT(str == Data_.ng_for_string_callsThis_is_test_string_for_string_calls()); - + str = strorg; typename TStringType::iterator b = str.begin(); typename TStringType::const_iterator s = str.begin() + str.size() / 2 - 1; typename TStringType::const_iterator e = str.end(); str.insert(b, s, e); UNIT_ASSERT(str == Data_.ng_for_string_callsThis_is_test_string_for_string_calls()); - -#if 0 + +#if 0 // AV str = strorg; str.insert(str.begin(), str.begin() + str.size() / 2 - 1, str.end()); UNIT_ASSERT(str == Data.ng_for_string_callsThis_is_test_string_for_string_calls()); -#endif - +#endif + TStringType str0; str0.insert(str0.begin(), 5, *Data_._0()); UNIT_ASSERT(str0 == Data_._00000()); - + TStringType str1; { typename TStringType::size_type pos = 0, nb = 2; str1.insert(pos, nb, *Data_._1()); } UNIT_ASSERT(str1 == Data_._11()); - + str0.insert(0, str1); UNIT_ASSERT(str0 == Data_._1100000()); - + TStringType str2(Data_._2345()); str0.insert(str0.size(), str2, 1, 2); UNIT_ASSERT(str0 == Data_._110000034()); - + str1.insert(str1.begin() + 1, 2, *Data_._2()); UNIT_ASSERT(str1 == Data_._1221()); - + str1.insert(2, Data_._333333(), 3); UNIT_ASSERT(str1 == Data_._1233321()); - + str1.insert(4, Data_._4444()); UNIT_ASSERT(str1 == Data_._12334444321()); - + str1.insert(str1.begin() + 6, *Data_._5()); UNIT_ASSERT(str1 == Data_._123344544321()); } - + void resize() { TStringType s; - + s.resize(0); - + UNIT_ASSERT(*s.c_str() == 0); - + s = Data_._1234567(); - + s.resize(0); UNIT_ASSERT(*s.c_str() == 0); - + s = Data_._1234567(); s.resize(1); UNIT_ASSERT(s.size() == 1); UNIT_ASSERT(*s.c_str() == *Data_._1()); UNIT_ASSERT(*(s.c_str() + 1) == 0); - + s = Data_._1234567(); -#if 0 +#if 0 s.resize(10); -#else +#else s.resize(10, 0); -#endif +#endif UNIT_ASSERT(s.size() == 10); UNIT_ASSERT(s[6] == *Data_._7()); UNIT_ASSERT(s[7] == 0); UNIT_ASSERT(s[8] == 0); UNIT_ASSERT(s[9] == 0); } - + void find() { TStringType s(Data_.one_two_three_one_two_three()); - + UNIT_ASSERT(s.find(Data_.one()) == 0); UNIT_ASSERT(s.find(*Data_.t()) == 4); UNIT_ASSERT(s.find(*Data_.t(), 5) == 8); - + UNIT_ASSERT(s.find(Data_.four()) == TStringType::npos); UNIT_ASSERT(s.find(Data_.one(), TStringType::npos) == TStringType::npos); UNIT_ASSERT(s.find_first_of(Data_.abcde()) == 2); UNIT_ASSERT(s.find_first_not_of(Data_.enotw_()) == 9); } - + void capacity() { TStringType s; - + UNIT_ASSERT(s.capacity() < s.max_size()); UNIT_ASSERT(s.capacity() >= s.size()); @@ -484,31 +484,31 @@ protected: UNIT_ASSERT(s.capacity() < s.max_size()); UNIT_ASSERT(s.capacity() >= s.size()); } - } - + } + void assign() { TStringType s; TChar const* cstr = Data_.test_string_for_assign(); - + s.assign(cstr, cstr + 22); UNIT_ASSERT(s == Data_.test_string_for_assign()); - + TStringType s2(Data_.other_test_string()); s.assign(s2); UNIT_ASSERT(s == s2); - + static TStringType str1; static TStringType str2; - + // short TStringType optim: str1 = Data_._123456(); // longer than short TStringType: str2 = Data_._1234567890123456789012345678901234567890(); - + UNIT_ASSERT(str1[5] == *Data_._6()); UNIT_ASSERT(str2[29] == *Data_._0()); } - + void copy() { TStringType s(Data_.foo()); TChar dest[4]; @@ -519,24 +519,24 @@ protected: UNIT_ASSERT(dest[pos++] == *Data_.o()); UNIT_ASSERT(dest[pos++] == *Data_.o()); UNIT_ASSERT(dest[pos++] == 1); - + dest[0] = dest[1] = dest[2] = dest[3] = 1; s.copy(dest, 4, 2); pos = 0; UNIT_ASSERT(dest[pos++] == *Data_.o()); UNIT_ASSERT(dest[pos++] == 1); - + // @todo use UNIT_TEST_EXCEPTION try { s.copy(dest, 4, 5); UNIT_ASSERT(!"expected std::out_of_range"); } catch (const std::out_of_range&) { UNIT_ASSERT(true); - } catch (...) { + } catch (...) { UNIT_ASSERT(!"expected std::out_of_range"); } - } - + } + void cbegin_cend() { const char helloThere[] = "Hello there"; TString s = helloThere; @@ -549,7 +549,7 @@ protected: void compare() { TStringType str1(Data_.abcdef()); TStringType str2; - + str2 = Data_.abcdef(); UNIT_ASSERT(str1.compare(str2) == 0); UNIT_ASSERT(str1.compare(str2.data(), str2.size()) == 0); @@ -559,28 +559,28 @@ protected: str2 = Data_.abcdefg(); UNIT_ASSERT(str1.compare(str2) < 0); UNIT_ASSERT(str1.compare(str2.data(), str2.size()) < 0); - + UNIT_ASSERT(str1.compare(Data_.abcdef()) == 0); UNIT_ASSERT(str1.compare(Data_.abcde()) > 0); UNIT_ASSERT(str1.compare(Data_.abcdefg()) < 0); - + str2 = Data_.cde(); UNIT_ASSERT(str1.compare(2, 3, str2) == 0); str2 = Data_.cd(); UNIT_ASSERT(str1.compare(2, 3, str2) > 0); str2 = Data_.cdef(); UNIT_ASSERT(str1.compare(2, 3, str2) < 0); - + str2 = Data_.abcdef(); UNIT_ASSERT(str1.compare(2, 3, str2, 2, 3) == 0); UNIT_ASSERT(str1.compare(2, 3, str2, 2, 2) > 0); UNIT_ASSERT(str1.compare(2, 3, str2, 2, 4) < 0); - + UNIT_ASSERT(str1.compare(2, 3, Data_.cdefgh(), 3) == 0); UNIT_ASSERT(str1.compare(2, 3, Data_.cdefgh(), 2) > 0); UNIT_ASSERT(str1.compare(2, 3, Data_.cdefgh(), 4) < 0); } - + void find_last_of() { // 21.3.6.4 TStringType s(Data_.one_two_three_one_two_three()); @@ -598,22 +598,22 @@ protected: UNIT_ASSERT(test.find_last_of(*Data_.a(), 1) == 0); UNIT_ASSERT(test.find_last_of(*Data_.a(), 0) == 0); } -#if 0 +#if 0 void rfind() { // 21.3.6.2 TStringType s(Data.one_two_three_one_two_three()); - + UNIT_ASSERT(s.rfind(Data.two()) == 18); UNIT_ASSERT(s.rfind(Data.two(), 0) == TStringType::npos); UNIT_ASSERT(s.rfind(Data.two(), 11) == 4); UNIT_ASSERT(s.rfind(*Data.w()) == 19); - + TStringType test(Data.aba()); - + UNIT_ASSERT(test.rfind(Data.a(), 2, 1) == 2); UNIT_ASSERT(test.rfind(Data.a(), 1, 1) == 0); UNIT_ASSERT(test.rfind(Data.a(), 0, 1) == 0); - + UNIT_ASSERT(test.rfind(*Data.a(), 2) == 2); UNIT_ASSERT(test.rfind(*Data.a(), 1) == 0); UNIT_ASSERT(test.rfind(*Data.a(), 0) == 0); @@ -622,18 +622,18 @@ protected: void find_last_not_of() { // 21.3.6.6 TStringType s(Data_.one_two_three_one_two_three()); - + UNIT_ASSERT(s.find_last_not_of(Data_.ehortw_()) == 15); - + TStringType test(Data_.aba()); - + UNIT_ASSERT(test.find_last_not_of(Data_.a(), 2, 1) == 1); UNIT_ASSERT(test.find_last_not_of(Data_.b(), 2, 1) == 2); UNIT_ASSERT(test.find_last_not_of(Data_.a(), 1, 1) == 1); UNIT_ASSERT(test.find_last_not_of(Data_.b(), 1, 1) == 0); UNIT_ASSERT(test.find_last_not_of(Data_.a(), 0, 1) == TStringType::npos); UNIT_ASSERT(test.find_last_not_of(Data_.b(), 0, 1) == 0); - + UNIT_ASSERT(test.find_last_not_of(*Data_.a(), 2) == 1); UNIT_ASSERT(test.find_last_not_of(*Data_.b(), 2) == 2); UNIT_ASSERT(test.find_last_not_of(*Data_.a(), 1) == 1); @@ -646,100 +646,100 @@ protected: // This test case is for the non template basic_TString::replace method, // this is why we play with the const iterators and reference to guaranty // that the right method is called. - + const TStringType v(Data._78()); TStringType s(Data._123456()); TStringType const& cs = s; - + typename TStringType::iterator i = s.begin() + 1; s.replace(i, i + 3, v.begin(), v.end()); - UNIT_ASSERT(s == Data._17856()); - + UNIT_ASSERT(s == Data._17856()); + s = Data._123456(); i = s.begin() + 1; s.replace(i, i + 1, v.begin(), v.end()); - UNIT_ASSERT(s == Data._1783456()); - + UNIT_ASSERT(s == Data._1783456()); + s = Data._123456(); i = s.begin() + 1; typename TStringType::const_iterator ci = s.begin() + 1; s.replace(i, i + 3, ci + 3, cs.end()); - UNIT_ASSERT(s == Data._15656()); - + UNIT_ASSERT(s == Data._15656()); + s = Data._123456(); i = s.begin() + 1; ci = s.begin() + 1; s.replace(i, i + 3, ci, ci + 2); - UNIT_ASSERT(s == Data._12356()); - + UNIT_ASSERT(s == Data._12356()); + s = Data._123456(); i = s.begin() + 1; ci = s.begin() + 1; s.replace(i, i + 3, ci + 1, cs.end()); - UNIT_ASSERT(s == Data._1345656()); - + UNIT_ASSERT(s == Data._1345656()); + s = Data._123456(); i = s.begin(); ci = s.begin() + 1; s.replace(i, i, ci, ci + 1); UNIT_ASSERT(s == Data._2123456()); - + s = Data._123456(); s.replace(s.begin() + 4, s.end(), cs.begin(), cs.end()); - UNIT_ASSERT(s == Data._1234123456()); - + UNIT_ASSERT(s == Data._1234123456()); + // This is the test for the template replace method. - + s = Data._123456(); typename TStringType::iterator b = s.begin() + 4; typename TStringType::iterator e = s.end(); typename TStringType::const_iterator rb = s.begin(); typename TStringType::const_iterator re = s.end(); s.replace(b, e, rb, re); - UNIT_ASSERT(s == Data._1234123456()); - + UNIT_ASSERT(s == Data._1234123456()); + s = Data._123456(); s.replace(s.begin() + 4, s.end(), s.begin(), s.end()); - UNIT_ASSERT(s == Data._1234123456()); - + UNIT_ASSERT(s == Data._1234123456()); + TStringType strorg(Data.This_is_test_StringT_for_StringT_calls()); TStringType str = strorg; str.replace(5, 15, str.c_str(), 10); - UNIT_ASSERT(str == Data.This_This_is_tefor_StringT_calls()); - + UNIT_ASSERT(str == Data.This_This_is_tefor_StringT_calls()); + str = strorg; str.replace(5, 5, str.c_str(), 10); - UNIT_ASSERT(str == Data.This_This_is_test_StringT_for_StringT_calls()); - - #if !defined(STLPORT) || defined(_STLP_MEMBER_TEMPLATES) + UNIT_ASSERT(str == Data.This_This_is_test_StringT_for_StringT_calls()); + + #if !defined(STLPORT) || defined(_STLP_MEMBER_TEMPLATES) deque<TChar> cdeque; cdeque.push_back(*Data.I()); str.replace(str.begin(), str.begin() + 11, cdeque.begin(), cdeque.end()); - UNIT_ASSERT(str == Data.Is_test_StringT_for_StringT_calls()); - #endif + UNIT_ASSERT(str == Data.Is_test_StringT_for_StringT_calls()); + #endif } -#endif +#endif }; // TStringStdTestImpl class TStringTest: public TTestBase, private TStringTestImpl<TString, TTestData<char>> { public: UNIT_TEST_SUITE(TStringTest); UNIT_TEST(TestMaxSize); - UNIT_TEST(TestConstructors); - UNIT_TEST(TestReplace); + UNIT_TEST(TestConstructors); + UNIT_TEST(TestReplace); #ifndef TSTRING_IS_STD_STRING - UNIT_TEST(TestRefCount); + UNIT_TEST(TestRefCount); #endif - UNIT_TEST(TestFind); - UNIT_TEST(TestContains); - UNIT_TEST(TestOperators); - UNIT_TEST(TestMulOperators); - UNIT_TEST(TestFuncs); - UNIT_TEST(TestUtils); - UNIT_TEST(TestEmpty); - UNIT_TEST(TestJoin); - UNIT_TEST(TestCopy); - UNIT_TEST(TestStrCpy); + UNIT_TEST(TestFind); + UNIT_TEST(TestContains); + UNIT_TEST(TestOperators); + UNIT_TEST(TestMulOperators); + UNIT_TEST(TestFuncs); + UNIT_TEST(TestUtils); + UNIT_TEST(TestEmpty); + UNIT_TEST(TestJoin); + UNIT_TEST(TestCopy); + UNIT_TEST(TestStrCpy); UNIT_TEST(TestPrefixSuffix); #ifndef TSTRING_IS_STD_STRING UNIT_TEST(TestCharRef); @@ -751,7 +751,7 @@ public: UNIT_TEST(TestAppendUtf16) UNIT_TEST(TestFillingAssign) UNIT_TEST(TestStdStreamApi) - //UNIT_TEST(TestOperatorsCI); must fail + //UNIT_TEST(TestOperatorsCI); must fail UNIT_TEST_SUITE_END(); void TestAppendUtf16() { @@ -772,10 +772,10 @@ public: UNIT_ASSERT_VALUES_EQUAL(data, ss.str()); - ss << '\n' - << data << std::endl; + ss << '\n' + << data << std::endl; - TString read = "xxx"; + TString read = "xxx"; ss >> read; UNIT_ASSERT_VALUES_EQUAL(read, data); } @@ -786,29 +786,29 @@ UNIT_TEST_SUITE_REGISTRATION(TStringTest); class TWideStringTest: public TTestBase, private TStringTestImpl<TUtf16String, TTestData<wchar16>> { public: UNIT_TEST_SUITE(TWideStringTest); - UNIT_TEST(TestConstructors); - UNIT_TEST(TestReplace); + UNIT_TEST(TestConstructors); + UNIT_TEST(TestReplace); #ifndef TSTRING_IS_STD_STRING - UNIT_TEST(TestRefCount); + UNIT_TEST(TestRefCount); #endif - UNIT_TEST(TestFind); - UNIT_TEST(TestContains); - UNIT_TEST(TestOperators); + UNIT_TEST(TestFind); + UNIT_TEST(TestContains); + UNIT_TEST(TestOperators); UNIT_TEST(TestLetOperator) - UNIT_TEST(TestMulOperators); - UNIT_TEST(TestFuncs); - UNIT_TEST(TestUtils); - UNIT_TEST(TestEmpty); - UNIT_TEST(TestJoin); - UNIT_TEST(TestCopy); - UNIT_TEST(TestStrCpy); + UNIT_TEST(TestMulOperators); + UNIT_TEST(TestFuncs); + UNIT_TEST(TestUtils); + UNIT_TEST(TestEmpty); + UNIT_TEST(TestJoin); + UNIT_TEST(TestCopy); + UNIT_TEST(TestStrCpy); UNIT_TEST(TestPrefixSuffix); #ifndef TSTRING_IS_STD_STRING UNIT_TEST(TestCharRef); #endif UNIT_TEST(TestBack); UNIT_TEST(TestFront) - UNIT_TEST(TestDecodingMethods); + UNIT_TEST(TestDecodingMethods); UNIT_TEST(TestIterators); UNIT_TEST(TestReverseIterators); UNIT_TEST(TestStringLiterals); @@ -833,11 +833,11 @@ private: UNIT_ASSERT(wtext.substr(5) == TUtf16String::FromAscii(text + 5)); const wchar16 wideCyrillicAlphabet[] = { - 0x0410, 0x0411, 0x0412, 0x0413, 0x0414, 0x0415, 0x0416, 0x0417, 0x0418, 0x0419, 0x041A, 0x041B, 0x041C, 0x041D, 0x041E, 0x041F, - 0x0420, 0x0421, 0x0422, 0x0423, 0x0424, 0x0425, 0x0426, 0x0427, 0x0428, 0x0429, 0x042A, 0x042B, 0x042C, 0x042D, 0x042E, 0x042F, - 0x0430, 0x0431, 0x0432, 0x0433, 0x0434, 0x0435, 0x0436, 0x0437, 0x0438, 0x0439, 0x043A, 0x043B, 0x043C, 0x043D, 0x043E, 0x043F, - 0x0440, 0x0441, 0x0442, 0x0443, 0x0444, 0x0445, 0x0446, 0x0447, 0x0448, 0x0449, 0x044A, 0x044B, 0x044C, 0x044D, 0x044E, 0x044F, - 0x00}; + 0x0410, 0x0411, 0x0412, 0x0413, 0x0414, 0x0415, 0x0416, 0x0417, 0x0418, 0x0419, 0x041A, 0x041B, 0x041C, 0x041D, 0x041E, 0x041F, + 0x0420, 0x0421, 0x0422, 0x0423, 0x0424, 0x0425, 0x0426, 0x0427, 0x0428, 0x0429, 0x042A, 0x042B, 0x042C, 0x042D, 0x042E, 0x042F, + 0x0430, 0x0431, 0x0432, 0x0433, 0x0434, 0x0435, 0x0436, 0x0437, 0x0438, 0x0439, 0x043A, 0x043B, 0x043C, 0x043D, 0x043E, 0x043F, + 0x0440, 0x0441, 0x0442, 0x0443, 0x0444, 0x0445, 0x0446, 0x0447, 0x0448, 0x0449, 0x044A, 0x044B, 0x044C, 0x044D, 0x044E, 0x044F, + 0x00}; TUtf16String strWide(wideCyrillicAlphabet); TString strUtf8 = WideToUTF8(strWide); @@ -907,7 +907,7 @@ private: UNIT_TEST_SUITE_REGISTRATION(TWideStringTest); -class TUtf32StringTest: public TTestBase, private TStringTestImpl<TUtf32String, TTestData<wchar32>> { +class TUtf32StringTest: public TTestBase, private TStringTestImpl<TUtf32String, TTestData<wchar32>> { public: UNIT_TEST_SUITE(TUtf32StringTest); UNIT_TEST(TestConstructors); @@ -1109,28 +1109,28 @@ class TStringStdTest: public TTestBase, private TStringStdTestImpl<TString, TTes public: UNIT_TEST_SUITE(TStringStdTest); UNIT_TEST(Constructor); - UNIT_TEST(reserve); - UNIT_TEST(short_string); - UNIT_TEST(erase); - UNIT_TEST(data); - UNIT_TEST(c_str); + UNIT_TEST(reserve); + UNIT_TEST(short_string); + UNIT_TEST(erase); + UNIT_TEST(data); + UNIT_TEST(c_str); UNIT_TEST(null_char_of_empty); - UNIT_TEST(null_char); + UNIT_TEST(null_char); UNIT_TEST(null_char_assignment_to_subscript_of_empty); UNIT_TEST(null_char_assignment_to_subscript_of_nonempty); #ifndef TSTRING_IS_STD_STRING UNIT_TEST(null_char_assignment_to_end_of_empty); UNIT_TEST(null_char_assignment_to_end_of_nonempty); #endif - UNIT_TEST(insert); - UNIT_TEST(resize); - UNIT_TEST(find); - UNIT_TEST(capacity); - UNIT_TEST(assign); - UNIT_TEST(copy); + UNIT_TEST(insert); + UNIT_TEST(resize); + UNIT_TEST(find); + UNIT_TEST(capacity); + UNIT_TEST(assign); + UNIT_TEST(copy); UNIT_TEST(cbegin_cend); - UNIT_TEST(compare); - UNIT_TEST(find_last_of); + UNIT_TEST(compare); + UNIT_TEST(find_last_of); #if 0 UNIT_TEST(rfind); UNIT_TEST(replace); @@ -1145,28 +1145,28 @@ class TWideStringStdTest: public TTestBase, private TStringStdTestImpl<TUtf16Str public: UNIT_TEST_SUITE(TWideStringStdTest); UNIT_TEST(Constructor); - UNIT_TEST(reserve); - UNIT_TEST(short_string); - UNIT_TEST(erase); - UNIT_TEST(data); - UNIT_TEST(c_str); + UNIT_TEST(reserve); + UNIT_TEST(short_string); + UNIT_TEST(erase); + UNIT_TEST(data); + UNIT_TEST(c_str); UNIT_TEST(null_char_of_empty); - UNIT_TEST(null_char); + UNIT_TEST(null_char); UNIT_TEST(null_char_assignment_to_subscript_of_empty); UNIT_TEST(null_char_assignment_to_subscript_of_nonempty); #ifndef TSTRING_IS_STD_STRING UNIT_TEST(null_char_assignment_to_end_of_empty); UNIT_TEST(null_char_assignment_to_end_of_nonempty); #endif - UNIT_TEST(insert); - UNIT_TEST(resize); - UNIT_TEST(find); - UNIT_TEST(capacity); - UNIT_TEST(assign); - UNIT_TEST(copy); + UNIT_TEST(insert); + UNIT_TEST(resize); + UNIT_TEST(find); + UNIT_TEST(capacity); + UNIT_TEST(assign); + UNIT_TEST(copy); UNIT_TEST(cbegin_cend); - UNIT_TEST(compare); - UNIT_TEST(find_last_of); + UNIT_TEST(compare); + UNIT_TEST(find_last_of); #if 0 UNIT_TEST(rfind); UNIT_TEST(replace); @@ -1203,68 +1203,68 @@ Y_UNIT_TEST_SUITE(HashFunctorTests) { UNIT_ASSERT_VALUES_EQUAL(h(ptr), h(stdStr)); } } - -#if !defined(TSTRING_IS_STD_STRING) -Y_UNIT_TEST_SUITE(StdNonConformant) { - Y_UNIT_TEST(TestEraseNoThrow) { - TString x; - - LegacyErase(x, 10); - } - - Y_UNIT_TEST(TestReplaceNoThrow) { - TString x; - - LegacyReplace(x, 0, 0, "1"); - - UNIT_ASSERT_VALUES_EQUAL(x, "1"); - - LegacyReplace(x, 10, 0, "1"); - - UNIT_ASSERT_VALUES_EQUAL(x, "1"); - } - - Y_UNIT_TEST(TestNoAlias) { - TString s = "x"; - - s.AppendNoAlias("abc", 3); - - UNIT_ASSERT_VALUES_EQUAL(s, "xabc"); - UNIT_ASSERT_VALUES_EQUAL(TString(s.c_str()), "xabc"); - } -} -#endif - -Y_UNIT_TEST_SUITE(Interop) { - static void Mutate(std::string& s) { - s += "y"; - } - - static void Mutate(TString& s) { - Mutate(MutRef(s)); - } - - Y_UNIT_TEST(TestMutate) { - TString x = "x"; - - Mutate(x); - - UNIT_ASSERT_VALUES_EQUAL(x, "xy"); - } - - static std::string TransformStd(const std::string& s) { - return s + "y"; - } - - static TString Transform(const TString& s) { - return TransformStd(s); - } - - Y_UNIT_TEST(TestTransform) { - UNIT_ASSERT_VALUES_EQUAL(Transform(TString("x")), "xy"); - } - - Y_UNIT_TEST(TestTemp) { - UNIT_ASSERT_VALUES_EQUAL("x" + ConstRef(TString("y")), "xy"); - } -} + +#if !defined(TSTRING_IS_STD_STRING) +Y_UNIT_TEST_SUITE(StdNonConformant) { + Y_UNIT_TEST(TestEraseNoThrow) { + TString x; + + LegacyErase(x, 10); + } + + Y_UNIT_TEST(TestReplaceNoThrow) { + TString x; + + LegacyReplace(x, 0, 0, "1"); + + UNIT_ASSERT_VALUES_EQUAL(x, "1"); + + LegacyReplace(x, 10, 0, "1"); + + UNIT_ASSERT_VALUES_EQUAL(x, "1"); + } + + Y_UNIT_TEST(TestNoAlias) { + TString s = "x"; + + s.AppendNoAlias("abc", 3); + + UNIT_ASSERT_VALUES_EQUAL(s, "xabc"); + UNIT_ASSERT_VALUES_EQUAL(TString(s.c_str()), "xabc"); + } +} +#endif + +Y_UNIT_TEST_SUITE(Interop) { + static void Mutate(std::string& s) { + s += "y"; + } + + static void Mutate(TString& s) { + Mutate(MutRef(s)); + } + + Y_UNIT_TEST(TestMutate) { + TString x = "x"; + + Mutate(x); + + UNIT_ASSERT_VALUES_EQUAL(x, "xy"); + } + + static std::string TransformStd(const std::string& s) { + return s + "y"; + } + + static TString Transform(const TString& s) { + return TransformStd(s); + } + + Y_UNIT_TEST(TestTransform) { + UNIT_ASSERT_VALUES_EQUAL(Transform(TString("x")), "xy"); + } + + Y_UNIT_TEST(TestTemp) { + UNIT_ASSERT_VALUES_EQUAL("x" + ConstRef(TString("y")), "xy"); + } +} diff --git a/util/generic/string_ut.h b/util/generic/string_ut.h index cc4c5afb16..44bb10bdeb 100644 --- a/util/generic/string_ut.h +++ b/util/generic/string_ut.h @@ -1,7 +1,7 @@ #pragma once #include "string.h" - + #include <library/cpp/testing/unittest/registar.h> #include <util/string/reverse.h> @@ -34,7 +34,7 @@ struct TCharBuffer<char, 0> { return Data; } }; - + #define DECLARE_AND_RETURN_BUFFER(s) \ static TCharBuffer<CharT, sizeof(s)> buf(s); \ return buf.GetData(); @@ -509,13 +509,13 @@ size_t TTestData<wchar16>::HashOf_0123456() { } template <class TStringType, typename TTestData> -class TStringTestImpl { +class TStringTestImpl { protected: using char_type = typename TStringType::char_type; using traits_type = typename TStringType::traits_type; - + TTestData Data; - + public: void TestMaxSize() { const size_t badMaxVal = TStringType{}.max_size() + 1; @@ -524,7 +524,7 @@ public: UNIT_CHECK_GENERATED_EXCEPTION(s.reserve(badMaxVal), std::length_error); } - void TestConstructors() { + void TestConstructors() { TStringType s0(nullptr); UNIT_ASSERT(s0.size() == 0); UNIT_ASSERT_EQUAL(s0, TStringType()); @@ -533,7 +533,7 @@ public: TStringType s1(*Data._0()); TStringType s2(Data._0()); UNIT_ASSERT(s1 == s2); - + TStringType fromZero(0); UNIT_ASSERT_VALUES_EQUAL(fromZero.size(), 0u); @@ -545,13 +545,13 @@ public: TStringType s3 = TStringType::Uninitialized(10); UNIT_ASSERT(s3.size() == 10); #endif - + TStringType s4(Data._0123456(), 1, 3); UNIT_ASSERT(s4 == Data._123()); - + TStringType s5(5, *Data._0()); UNIT_ASSERT(s5 == Data._00000()); - + TStringType s6(Data._0123456()); UNIT_ASSERT(s6 == Data._0123456()); TStringType s7(s6); @@ -559,7 +559,7 @@ public: #ifndef TSTRING_IS_STD_STRING UNIT_ASSERT(s7.c_str() == s6.c_str()); #endif - + TStringType s8(s7, 1, 3); UNIT_ASSERT(s8 == Data._123()); @@ -570,11 +570,11 @@ public: UNIT_ASSERT(s10.empty()); UNIT_ASSERT(s10.capacity() >= 100); } - - void TestReplace() { + + void TestReplace() { TStringType s(Data._0123456()); UNIT_ASSERT(s.copy() == Data._0123456()); - + // append family s.append(Data.x()); UNIT_ASSERT(s == Data._0123456x()); @@ -651,13 +651,13 @@ public: } #ifndef TSTRING_IS_STD_STRING - void TestRefCount() { - using TStr = TStringType; - - struct TestStroka: public TStr { - using TStr::TStr; - // un-protect - using TStr::RefCount; + void TestRefCount() { + using TStr = TStringType; + + struct TestStroka: public TStr { + using TStr::TStr; + // un-protect + using TStr::RefCount; }; TestStroka s1(Data.orig()); @@ -675,8 +675,8 @@ public: #endif // Find family - - void TestFind() { + + void TestFind() { const TStringType s(Data._0123456_12345()); const TStringType s2(Data._0123()); @@ -722,7 +722,7 @@ public: UNIT_ASSERT(s.rfind(TStringType(Data._345()), 2) == TStringType::npos); } - void TestContains() { + void TestContains() { const TStringType s(Data._0123456_12345()); const TStringType s2(Data._0123()); @@ -740,8 +740,8 @@ public: } // Operators - - void TestOperators() { + + void TestOperators() { TStringType s(Data._0123456()); // operator += @@ -792,7 +792,7 @@ public: UNIT_ASSERT_EQUAL(Data.xyz() >= s, true); } - void TestOperatorsCI() { + void TestOperatorsCI() { TStringType s(Data.ABCD()); UNIT_ASSERT(s > Data.abc0123456xyz()); UNIT_ASSERT(s == Data.abcd()); @@ -804,7 +804,7 @@ public: UNIT_ASSERT(s == TCIStringBuf(Data.abcd())); } - void TestMulOperators() { + void TestMulOperators() { { TStringType s(Data._0()); s *= 10; @@ -817,8 +817,8 @@ public: } // Test any other functions - - void TestFuncs() { + + void TestFuncs() { TStringType s(Data._0123456()); UNIT_ASSERT(s.c_str() == s.data()); @@ -897,7 +897,7 @@ public: ComputeHash(sS); /*size_t hash_val = sS.hash(); try { - //UNIT_ASSERT(hash_val == Data.HashOf_0123456()); + //UNIT_ASSERT(hash_val == Data.HashOf_0123456()); } catch (...) { Cerr << hash_val << Endl; throw; @@ -907,13 +907,13 @@ public: UNIT_ASSERT(s2 == Data._23()); //s2.reserve(); - + TStringType s5(Data.abcde()); s5.clear(); UNIT_ASSERT(s5 == Data.Empty()); } - void TestUtils() { + void TestUtils() { TStringType s; s = Data._01230123(); TStringType from = Data._0(); @@ -923,13 +923,13 @@ public: UNIT_ASSERT(s == Data.z123z123()); } - void TestEmpty() { + void TestEmpty() { TStringType s; s = Data._2(); s = TStringType(Data.fdfdsfds(), (size_t)0, (size_t)0); UNIT_ASSERT(s.empty()); } - + void TestJoin() { UNIT_ASSERT_EQUAL(TStringType::Join(Data._12(), Data._3456()), Data._123456()); UNIT_ASSERT_EQUAL(TStringType::Join(Data._12(), TStringType(Data._3456())), Data._123456()); @@ -939,8 +939,8 @@ public: UNIT_ASSERT_EQUAL(TStringType::Join(TStringType(Data._12()), TStringType(Data._345()), Data._6()), Data._123456()); UNIT_ASSERT_EQUAL(TStringType::Join(TStringType(Data.a()), Data.b(), TStringType(Data.cd()), TStringType(Data.e()), Data.fg(), TStringType(Data.h())), Data.abcdefgh()); UNIT_ASSERT_EQUAL(TStringType::Join(TStringType(Data.a()), static_cast<typename TStringType::char_type>('b'), TStringType(Data.cd()), TStringType(Data.e()), Data.fg(), TStringType(Data.h())), Data.abcdefgh()); - } - + } + void TestCopy() { TStringType s(Data.abcd()); TStringType c = s.copy(); @@ -948,12 +948,12 @@ public: UNIT_ASSERT_EQUAL(s, c); UNIT_ASSERT(s.end() != c.end()); } - + void TestStrCpy() { { TStringType s(Data.abcd()); char_type data[5]; - + data[4] = 1; s.strcpy(data, 4); @@ -988,7 +988,7 @@ public: UNIT_ASSERT_EQUAL(emptyStr.StartsWith(emptyStr), true); UNIT_ASSERT_EQUAL(emptyStr.EndsWith(emptyStr), true); - const char_type chars[] = {'h', 'e', 'l', 'l', 'o', 0}; + const char_type chars[] = {'h', 'e', 'l', 'l', 'o', 0}; const TStringType str(chars); UNIT_ASSERT_EQUAL(str.StartsWith('h'), true); UNIT_ASSERT_EQUAL(str.StartsWith('o'), false); @@ -1000,9 +1000,9 @@ public: #ifndef TSTRING_IS_STD_STRING void TestCharRef() { - const char_type abc[] = {'a', 'b', 'c', 0}; - const char_type bbc[] = {'b', 'b', 'c', 0}; - const char_type cbc[] = {'c', 'b', 'c', 0}; + const char_type abc[] = {'a', 'b', 'c', 0}; + const char_type bbc[] = {'b', 'b', 'c', 0}; + const char_type cbc[] = {'c', 'b', 'c', 0}; TStringType s0 = abc; TStringType s1 = s0; diff --git a/util/generic/typelist.cpp b/util/generic/typelist.cpp index 0b11b3389b..275b565ddb 100644 --- a/util/generic/typelist.cpp +++ b/util/generic/typelist.cpp @@ -1,5 +1,5 @@ -#include "typelist.h" - +#include "typelist.h" + static_assert( TSignedInts::THave<char>::value, "char type in Arcadia must be signed; add -fsigned-char to compiler options"); diff --git a/util/generic/typelist.h b/util/generic/typelist.h index ea169f8188..5ce26ab97c 100644 --- a/util/generic/typelist.h +++ b/util/generic/typelist.h @@ -1,63 +1,63 @@ #pragma once - + #include <util/system/types.h> #include <util/generic/typetraits.h> #include <type_traits> -template <class... R> +template <class... R> struct TTypeList; -namespace NTL { - template <unsigned N, typename TL> - struct TGetImpl { +namespace NTL { + template <unsigned N, typename TL> + struct TGetImpl { using type = typename TGetImpl<N - 1, typename TL::TTail>::type; - }; - - template <typename TL> - struct TGetImpl<0u, TL> { + }; + + template <typename TL> + struct TGetImpl<0u, TL> { using type = typename TL::THead; - }; -} - -template <> + }; +} + +template <> struct TTypeList<> { static constexpr size_t Length = 0; - + template <class> using THave = std::false_type; - - template <template <class> class P> - struct TSelectBy { + + template <template <class> class P> + struct TSelectBy { using type = TTypeList<>; - }; -}; - + }; +}; + using TNone = TTypeList<>; - -template <class H, class... R> + +template <class H, class... R> struct TTypeList<H, R...> { using THead = H; using TTail = TTypeList<R...>; static constexpr size_t Length = 1 + sizeof...(R); - - template <class V> + + template <class V> using THave = TDisjunction<std::is_same<H, V>, typename TTail::template THave<V>>; - - template <unsigned N> + + template <unsigned N> using TGet = typename ::NTL::TGetImpl<N, TTypeList<H, R...>>::type; - - template <template <class> class P> - struct TSelectBy { + + template <template <class> class P> + struct TSelectBy { using type = std::conditional_t<P<THead>::value, THead, typename TTail::template TSelectBy<P>::type>; - }; -}; - + }; +}; + //FIXME: temporary to check overall build -template <class T> -struct TTypeList<T, TNone>: public TTypeList<T> { +template <class T> +struct TTypeList<T, TNone>: public TTypeList<T> { }; using TCommonSignedInts = TTypeList<signed char, signed short, signed int, signed long, signed long long>; @@ -66,43 +66,43 @@ using TFixedWidthSignedInts = TTypeList<i8, i16, i32, i64>; using TFixedWidthUnsignedInts = TTypeList<ui8, ui16, ui32, ui64>; using TFloats = TTypeList<float, double, long double>; -namespace NTL { - template <class T1, class T2> +namespace NTL { + template <class T1, class T2> struct TConcat; - template <class... R1, class... R2> + template <class... R1, class... R2> struct TConcat<TTypeList<R1...>, TTypeList<R2...>> { using type = TTypeList<R1..., R2...>; }; - template <bool isSigned, class T, class TS, class TU> - struct TTypeSelectorBase { + template <bool isSigned, class T, class TS, class TU> + struct TTypeSelectorBase { using TSignedInts = typename TConcat<TTypeList<T>, TS>::type; using TUnsignedInts = TU; - }; + }; - template <class T, class TS, class TU> - struct TTypeSelectorBase<false, T, TS, TU> { + template <class T, class TS, class TU> + struct TTypeSelectorBase<false, T, TS, TU> { using TSignedInts = TS; using TUnsignedInts = typename TConcat<TTypeList<T>, TU>::type; - }; - - template <class T, class TS, class TU> - struct TTypeSelector: public TTypeSelectorBase<((T)(-1) < 0), T, TS, TU> { - }; - + }; + + template <class T, class TS, class TU> + struct TTypeSelector: public TTypeSelectorBase<((T)(-1) < 0), T, TS, TU> { + }; + using T1 = TTypeSelector<char, TCommonSignedInts, TCommonUnsignedInts>; using T2 = TTypeSelector<wchar_t, T1::TSignedInts, T1::TUnsignedInts>; -} - +} + using TSignedInts = NTL::T2::TSignedInts; using TUnsignedInts = NTL::T2::TUnsignedInts; - -template <unsigned sizeOf> -struct TSizeOfPredicate { - template <class T> + +template <unsigned sizeOf> +struct TSizeOfPredicate { + template <class T> using TResult = TBoolConstant<sizeof(T) == sizeOf>; -}; +}; template <typename T> using TFixedWidthSignedInt = typename TFixedWidthSignedInts::template TSelectBy<TSizeOfPredicate<sizeof(T)>::template TResult>::type; diff --git a/util/generic/typelist_ut.cpp b/util/generic/typelist_ut.cpp index 06f4f997dc..eeabfa97b1 100644 --- a/util/generic/typelist_ut.cpp +++ b/util/generic/typelist_ut.cpp @@ -1,28 +1,28 @@ #include <library/cpp/testing/unittest/registar.h> #include <util/system/type_name.h> -#include "typelist.h" -#include "vector.h" -#include "map.h" +#include "typelist.h" +#include "vector.h" +#include "map.h" class TTypeListTest: public TTestBase { UNIT_TEST_SUITE(TTypeListTest); UNIT_TEST(TestSimple); UNIT_TEST(TestHave); - UNIT_TEST(TestGet); + UNIT_TEST(TestGet); UNIT_TEST(TestFloatList); UNIT_TEST(TestSelectBy); UNIT_TEST_SUITE_END(); public: - void TestGet() { + void TestGet() { using TListType = TTypeList<int, char, float>; - + UNIT_ASSERT_TYPES_EQUAL(TListType::TGet<0>, int); UNIT_ASSERT_TYPES_EQUAL(TListType::TGet<1>, char); UNIT_ASSERT_TYPES_EQUAL(TListType::TGet<2>, float); - } - + } + void TestSimple() { using TListType = TTypeList<int, char, float>; UNIT_ASSERT_EQUAL(TListType::Length, 3); @@ -41,28 +41,28 @@ public: UNIT_ASSERT(!TListType::THave<TC&>::value); } - template <class T> - class TT {}; + template <class T> + class TT {}; - template <class T> - struct TIs1ArgTemplate: std::false_type {}; + template <class T> + struct TIs1ArgTemplate: std::false_type {}; - template <class T, template <class> class TT> - struct TIs1ArgTemplate<TT<T>>: std::true_type {}; + template <class T, template <class> class TT> + struct TIs1ArgTemplate<TT<T>>: std::true_type {}; - template <class T> - struct TIsNArgTemplate: std::false_type {}; + template <class T> + struct TIsNArgTemplate: std::false_type {}; - template <template <class...> class TT, class... R> - struct TIsNArgTemplate<TT<R...>>: std::true_type {}; + template <template <class...> class TT, class... R> + struct TIsNArgTemplate<TT<R...>>: std::true_type {}; - template <class> - struct TAnyType: std::true_type {}; + template <class> + struct TAnyType: std::true_type {}; - template <class T> + template <class T> struct TMyVector {}; - template <class T1, class T2> + template <class T1, class T2> struct TMyMap {}; void TestSelectBy() { diff --git a/util/generic/typetraits.cpp b/util/generic/typetraits.cpp index 45fd68ff8c..7eadd13559 100644 --- a/util/generic/typetraits.cpp +++ b/util/generic/typetraits.cpp @@ -1 +1 @@ -#include "typetraits.h" +#include "typetraits.h" diff --git a/util/generic/typetraits.h b/util/generic/typetraits.h index 8427bd2cd8..d165bd1a06 100644 --- a/util/generic/typetraits.h +++ b/util/generic/typetraits.h @@ -1,11 +1,11 @@ #pragma once - + #include "va_args.h" - -#include <util/system/defaults.h> - + +#include <util/system/defaults.h> + #include <iterator> -#include <type_traits> +#include <type_traits> #include <stlfwd> #if _LIBCPP_STD_VER >= 17 @@ -13,7 +13,7 @@ template <bool B> using TBoolConstant = std::bool_constant<B>; #else template <bool B> -struct TBoolConstant: std::integral_constant<bool, B> {}; +struct TBoolConstant: std::integral_constant<bool, B> {}; #endif #if _LIBCPP_STD_VER >= 17 @@ -21,13 +21,13 @@ template <class B> using TNegation = std::negation<B>; #else template <class B> -struct TNegation: ::TBoolConstant<!bool(B::value)> {}; +struct TNegation: ::TBoolConstant<!bool(B::value)> {}; #endif namespace NPrivate { template <class... Bs> constexpr bool ConjunctionImpl() { - bool bs[] = {(bool)Bs::value...}; + bool bs[] = {(bool)Bs::value...}; for (auto b : bs) { if (!b) { return false; @@ -38,7 +38,7 @@ namespace NPrivate { template <class... Bs> constexpr bool DisjunctionImpl() { - bool bs[] = {(bool)Bs::value...}; + bool bs[] = {(bool)Bs::value...}; for (auto b : bs) { if (b) { return true; @@ -54,7 +54,7 @@ template <class... Bs> using TConjunction = std::conjunction<Bs...>; #else template <class... Bs> -struct TConjunction: ::TBoolConstant<::NPrivate::ConjunctionImpl<Bs...>()> {}; +struct TConjunction: ::TBoolConstant<::NPrivate::ConjunctionImpl<Bs...>()> {}; #endif #if _LIBCPP_STD_VER >= 17 && !defined(_MSC_VER) @@ -65,7 +65,7 @@ template <class... Bs> using TDisjunction = std::disjunction<Bs...>; #else template <class... Bs> -struct TDisjunction: ::TBoolConstant<::NPrivate::DisjunctionImpl<Bs...>()> {}; +struct TDisjunction: ::TBoolConstant<::NPrivate::DisjunctionImpl<Bs...>()> {}; #endif #if _LIBCPP_STD_VER >= 17 @@ -77,89 +77,89 @@ using TVoidT = void; #endif template <class T> -struct TPodTraits { - enum { - IsPod = false - }; -}; - -template <class T> -class TTypeTraitsBase { -public: - static constexpr bool IsPod = (TPodTraits<std::remove_cv_t<T>>::IsPod || std::is_scalar<std::remove_all_extents_t<T>>::value || - TPodTraits<std::remove_cv_t<std::remove_all_extents_t<T>>>::IsPod); -}; - +struct TPodTraits { + enum { + IsPod = false + }; +}; + +template <class T> +class TTypeTraitsBase { +public: + static constexpr bool IsPod = (TPodTraits<std::remove_cv_t<T>>::IsPod || std::is_scalar<std::remove_all_extents_t<T>>::value || + TPodTraits<std::remove_cv_t<std::remove_all_extents_t<T>>>::IsPod); +}; + namespace NPrivate { template <class T> - struct TIsSmall: std::integral_constant<bool, (sizeof(T) <= sizeof(void*))> {}; + struct TIsSmall: std::integral_constant<bool, (sizeof(T) <= sizeof(void*))> {}; } -template <class T> -class TTypeTraits: public TTypeTraitsBase<T> { +template <class T> +class TTypeTraits: public TTypeTraitsBase<T> { using TBase = TTypeTraitsBase<T>; - - /* - * can be effectively passed to function as value - */ + + /* + * can be effectively passed to function as value + */ static constexpr bool IsValueType = std::is_scalar<T>::value || std::is_array<T>::value || std::is_reference<T>::value || (TBase::IsPod && - std::conditional_t< - std::is_function<T>::value, - std::false_type, - ::NPrivate::TIsSmall<T>>::value); - + std::conditional_t< + std::is_function<T>::value, + std::false_type, + ::NPrivate::TIsSmall<T>>::value); + public: - /* - * can be used in function templates for effective parameters passing - */ + /* + * can be used in function templates for effective parameters passing + */ using TFuncParam = std::conditional_t<IsValueType, T, const std::remove_reference_t<T>&>; -}; - -template <> -class TTypeTraits<void>: public TTypeTraitsBase<void> {}; - -#define Y_DECLARE_PODTYPE(type) \ - template <> \ - struct TPodTraits<type> { \ - enum { IsPod = true }; \ - } - -#define Y_HAS_MEMBER_IMPL_2(method, name) \ - template <class T> \ - struct TClassHas##name { \ - struct TBase { \ - void method(); \ - }; \ - class THelper: public T, public TBase { \ - public: \ - template <class T1> \ - inline THelper(const T1& = T1()) { \ - } \ - }; \ - template <class T1, T1 val> \ - class TChecker {}; \ - struct TNo { \ - char ch; \ - }; \ - struct TYes { \ - char arr[2]; \ - }; \ - template <class T1> \ - static TNo CheckMember(T1*, TChecker<void (TBase::*)(), &T1::method>* = nullptr); \ - static TYes CheckMember(...); \ - static constexpr bool value = \ - (sizeof(TYes) == sizeof(CheckMember((THelper*)nullptr))); \ - }; \ - template <class T, bool isClassType> \ - struct TBaseHas##name: std::false_type {}; \ - template <class T> \ - struct TBaseHas##name<T, true> \ - : std::integral_constant<bool, TClassHas##name<T>::value> {}; \ - template <class T> \ - struct THas##name \ +}; + +template <> +class TTypeTraits<void>: public TTypeTraitsBase<void> {}; + +#define Y_DECLARE_PODTYPE(type) \ + template <> \ + struct TPodTraits<type> { \ + enum { IsPod = true }; \ + } + +#define Y_HAS_MEMBER_IMPL_2(method, name) \ + template <class T> \ + struct TClassHas##name { \ + struct TBase { \ + void method(); \ + }; \ + class THelper: public T, public TBase { \ + public: \ + template <class T1> \ + inline THelper(const T1& = T1()) { \ + } \ + }; \ + template <class T1, T1 val> \ + class TChecker {}; \ + struct TNo { \ + char ch; \ + }; \ + struct TYes { \ + char arr[2]; \ + }; \ + template <class T1> \ + static TNo CheckMember(T1*, TChecker<void (TBase::*)(), &T1::method>* = nullptr); \ + static TYes CheckMember(...); \ + static constexpr bool value = \ + (sizeof(TYes) == sizeof(CheckMember((THelper*)nullptr))); \ + }; \ + template <class T, bool isClassType> \ + struct TBaseHas##name: std::false_type {}; \ + template <class T> \ + struct TBaseHas##name<T, true> \ + : std::integral_constant<bool, TClassHas##name<T>::value> {}; \ + template <class T> \ + struct THas##name \ : TBaseHas##name<T, std::is_class<T>::value || std::is_union<T>::value> {} #define Y_HAS_MEMBER_IMPL_1(name) Y_HAS_MEMBER_IMPL_2(name, name) @@ -193,11 +193,11 @@ class TTypeTraits<void>: public TTypeTraitsBase<void> {}; */ #define Y_HAS_MEMBER(...) Y_PASS_VA_ARGS(Y_MACRO_IMPL_DISPATCHER_2(__VA_ARGS__, Y_HAS_MEMBER_IMPL_2, Y_HAS_MEMBER_IMPL_1)(__VA_ARGS__)) -#define Y_HAS_SUBTYPE_IMPL_2(subtype, name) \ - template <class T, class = void> \ - struct THas##name: std::false_type {}; \ - template <class T> \ - struct THas##name<T, ::TVoidT<typename T::subtype>>: std::true_type {}; +#define Y_HAS_SUBTYPE_IMPL_2(subtype, name) \ + template <class T, class = void> \ + struct THas##name: std::false_type {}; \ + template <class T> \ + struct THas##name<T, ::TVoidT<typename T::subtype>>: std::true_type {}; #define Y_HAS_SUBTYPE_IMPL_1(name) Y_HAS_SUBTYPE_IMPL_2(name, name) @@ -236,38 +236,38 @@ struct TPodTraits<std::pair<T1, T2>> { }; template <class T> -struct TIsPointerToConstMemberFunction: std::false_type { -}; +struct TIsPointerToConstMemberFunction: std::false_type { +}; -template <class R, class T, class... Args> -struct TIsPointerToConstMemberFunction<R (T::*)(Args...) const>: std::true_type { -}; +template <class R, class T, class... Args> +struct TIsPointerToConstMemberFunction<R (T::*)(Args...) const>: std::true_type { +}; -template <class R, class T, class... Args> -struct TIsPointerToConstMemberFunction<R (T::*)(Args...) const&>: std::true_type { -}; +template <class R, class T, class... Args> +struct TIsPointerToConstMemberFunction<R (T::*)(Args...) const&>: std::true_type { +}; -template <class R, class T, class... Args> -struct TIsPointerToConstMemberFunction<R (T::*)(Args...) const&&>: std::true_type { -}; +template <class R, class T, class... Args> +struct TIsPointerToConstMemberFunction<R (T::*)(Args...) const&&>: std::true_type { +}; -template <class R, class T, class... Args> -struct TIsPointerToConstMemberFunction<R (T::*)(Args..., ...) const>: std::true_type { -}; +template <class R, class T, class... Args> +struct TIsPointerToConstMemberFunction<R (T::*)(Args..., ...) const>: std::true_type { +}; -template <class R, class T, class... Args> -struct TIsPointerToConstMemberFunction<R (T::*)(Args..., ...) const&>: std::true_type { -}; +template <class R, class T, class... Args> +struct TIsPointerToConstMemberFunction<R (T::*)(Args..., ...) const&>: std::true_type { +}; -template <class R, class T, class... Args> -struct TIsPointerToConstMemberFunction<R (T::*)(Args..., ...) const&&>: std::true_type { -}; +template <class R, class T, class... Args> +struct TIsPointerToConstMemberFunction<R (T::*)(Args..., ...) const&&>: std::true_type { +}; template <template <class...> class T, class U> -struct TIsSpecializationOf: std::false_type {}; +struct TIsSpecializationOf: std::false_type {}; template <template <class...> class T, class... Ts> -struct TIsSpecializationOf<T, T<Ts...>>: std::true_type {}; +struct TIsSpecializationOf<T, T<Ts...>>: std::true_type {}; /* * TDependentFalse is a constant dependent on a template parameter. @@ -280,7 +280,7 @@ struct TIsSpecializationOf<T, T<Ts...>>: std::true_type {}; * static_assert(TDependentFalse<T>, "unknown type"); * } */ -template <typename... T> +template <typename... T> constexpr bool TDependentFalse = false; // FIXME: neither nvcc10 nor nvcc11 support using auto in this context @@ -288,7 +288,7 @@ constexpr bool TDependentFalse = false; template <size_t Value> constexpr bool TValueDependentFalse = false; #else -template <auto... Values> +template <auto... Values> constexpr bool TValueDependentFalse = false; #endif @@ -297,8 +297,8 @@ constexpr bool TValueDependentFalse = false; */ template <class T, class R = void> using TEnableIfTuple = std::enable_if_t<::TDisjunction<::TIsSpecializationOf<std::tuple, std::decay_t<T>>, - ::TIsSpecializationOf<std::pair, std::decay_t<T>>>::value, - R>; + ::TIsSpecializationOf<std::pair, std::decay_t<T>>>::value, + R>; namespace NPrivate { // To allow ADL with custom begin/end @@ -306,11 +306,11 @@ namespace NPrivate { using std::end; template <typename T> - auto IsIterableImpl(int) -> decltype( - begin(std::declval<T&>()) != end(std::declval<T&>()), // begin/end and operator != + auto IsIterableImpl(int) -> decltype( + begin(std::declval<T&>()) != end(std::declval<T&>()), // begin/end and operator != ++std::declval<decltype(begin(std::declval<T&>()))&>(), // operator ++ - *begin(std::declval<T&>()), // operator* - std::true_type{}); + *begin(std::declval<T&>()), // operator* + std::true_type{}); template <typename T> std::false_type IsIterableImpl(...); diff --git a/util/generic/typetraits_ut.cpp b/util/generic/typetraits_ut.cpp index 0bd2afb814..e7571c75ec 100644 --- a/util/generic/typetraits_ut.cpp +++ b/util/generic/typetraits_ut.cpp @@ -1,7 +1,7 @@ -#include "typetraits.h" - +#include "typetraits.h" + #include <library/cpp/testing/unittest/registar.h> - + #include <vector> #include <tuple> @@ -14,46 +14,46 @@ namespace { class TNonPodClass { TNonPodClass() { - } + } }; class TEmptyClass { - void operator()() const { - } + void operator()() const { + } }; class TAnotherEmptyClass { }; - class TEmptyDerivedClass: public TEmptyClass { + class TEmptyDerivedClass: public TEmptyClass { }; - class TEmptyMultiDerivedClass: public TEmptyDerivedClass, public TAnotherEmptyClass { + class TEmptyMultiDerivedClass: public TEmptyDerivedClass, public TAnotherEmptyClass { /* Not empty under MSVC. * MSVC's EBCO implementation can handle only one empty base class. */ }; - struct TNonEmptyClass { + struct TNonEmptyClass { TEmptyClass member; }; - class TNonEmptyDerivedClass: public TNonEmptyClass { + class TNonEmptyDerivedClass: public TNonEmptyClass { }; - class TStdLayoutClass1: public TEmptyClass { + class TStdLayoutClass1: public TEmptyClass { public: int Value1; int Value2; }; - class TStdLayoutClass2: public TNonEmptyClass { + class TStdLayoutClass2: public TNonEmptyClass { }; class TNonStdLayoutClass1 { public: int Value1; - - protected: + + protected: int Value2; }; @@ -63,10 +63,10 @@ namespace { } }; - class TNonStdLayoutClass3: public TNonStdLayoutClass2 { + class TNonStdLayoutClass3: public TNonStdLayoutClass2 { }; - class TNonStdLayoutClass4: public TEmptyClass { + class TNonStdLayoutClass4: public TEmptyClass { public: TEmptyClass Base; }; @@ -76,8 +76,8 @@ namespace { { \ const bool x_ = std::is_same<x, y>::value; \ UNIT_ASSERT_C(x_, #x " != " #y); \ - } - + } + Y_UNIT_TEST_SUITE(TTypeTraitsTest) { Y_UNIT_TEST(TestIsSame) { UNIT_ASSERT((std::is_same<int, int>::value)); @@ -91,52 +91,52 @@ Y_UNIT_TEST_SUITE(TTypeTraitsTest) { ASSERT_SAME_TYPE(std::remove_reference_t<const int&>, const int); ASSERT_SAME_TYPE(std::remove_reference_t<int&&>, int); ASSERT_SAME_TYPE(std::remove_reference_t<const int&&>, const int); - - class TIncompleteType; + + class TIncompleteType; ASSERT_SAME_TYPE(std::remove_reference_t<TIncompleteType&>, TIncompleteType); - } - + } + Y_UNIT_TEST(TestRemoveConst) { ASSERT_SAME_TYPE(std::remove_const_t<const int>, int); - } - + } + Y_UNIT_TEST(TestRemoveVolatile) { ASSERT_SAME_TYPE(std::remove_volatile_t<volatile int>, int); - } - + } + Y_UNIT_TEST(TestRemoveCV) { ASSERT_SAME_TYPE(std::remove_cv_t<const volatile int>, int); - } - + } + Y_UNIT_TEST(TestAddCV) { ASSERT_SAME_TYPE(std::add_cv_t<int>, const volatile int); - } - + } + Y_UNIT_TEST(TestClass) { UNIT_ASSERT(std::is_class<TString>::value); UNIT_ASSERT(!std::is_class<ETestEnum>::value); UNIT_ASSERT(!std::is_class<int>::value); UNIT_ASSERT(!std::is_class<void*>::value); - } - - template <class T> - inline void TestArithmeticType() { + } + + template <class T> + inline void TestArithmeticType() { UNIT_ASSERT(std::is_arithmetic<T>::value); UNIT_ASSERT(std::is_arithmetic<const T>::value); UNIT_ASSERT(std::is_arithmetic<volatile T>::value); UNIT_ASSERT(std::is_arithmetic<const volatile T>::value); - + UNIT_ASSERT(!std::is_arithmetic<T&>::value); UNIT_ASSERT(!std::is_arithmetic<T&&>::value); UNIT_ASSERT(!std::is_arithmetic<T*>::value); - bool a; + bool a; a = std::is_same<typename TTypeTraits<T>::TFuncParam, T>::value; - UNIT_ASSERT(a); + UNIT_ASSERT(a); a = std::is_same<typename TTypeTraits<const volatile T>::TFuncParam, const volatile T>::value; - UNIT_ASSERT(a); - } + UNIT_ASSERT(a); + } template <class T> inline void TestUnsignedIntType() { @@ -149,7 +149,7 @@ Y_UNIT_TEST_SUITE(TTypeTraitsTest) { UNIT_ASSERT(!std::is_unsigned<T&&>::value); UNIT_ASSERT(!std::is_unsigned<T*>::value); - enum ETypedEnum: T {}; + enum ETypedEnum: T {}; UNIT_ASSERT(!std::is_unsigned<ETypedEnum>::value); } @@ -164,7 +164,7 @@ Y_UNIT_TEST_SUITE(TTypeTraitsTest) { UNIT_ASSERT(!std::is_signed<T&&>::value); UNIT_ASSERT(!std::is_signed<T*>::value); - enum ETypedEnum: T {}; + enum ETypedEnum: T {}; UNIT_ASSERT(!std::is_signed<ETypedEnum>::value); } @@ -203,8 +203,8 @@ Y_UNIT_TEST_SUITE(TTypeTraitsTest) { ASSERT_SAME_TYPE(std::add_rvalue_reference_t<int*&>, int*&); ASSERT_SAME_TYPE(std::add_rvalue_reference_t<int&&>, int&&); ASSERT_SAME_TYPE(std::add_rvalue_reference_t<void>, void); - } - + } + Y_UNIT_TEST(TestIsEmpty) { UNIT_ASSERT(std::is_empty<TEmptyClass>::value); UNIT_ASSERT(std::is_empty<TEmptyDerivedClass>::value); @@ -216,7 +216,7 @@ Y_UNIT_TEST_SUITE(TTypeTraitsTest) { #endif UNIT_ASSERT(!std::is_empty<TNonEmptyClass>::value); UNIT_ASSERT(!std::is_empty<TNonEmptyDerivedClass>::value); - } + } Y_UNIT_TEST(TestIsStandardLayout) { UNIT_ASSERT(std::is_standard_layout<TStdLayoutClass1>::value); @@ -257,8 +257,8 @@ Y_UNIT_TEST_SUITE(TTypeTraitsTest) { UNIT_ASSERT(!std::is_trivially_copyable<TNonTriviallyCopyConstructible>::value); UNIT_ASSERT(!std::is_trivially_copyable<TNonTriviallyDestructible>::value); } -}; - +}; + namespace { template <typename T> struct TTypeTraitsExpected; @@ -288,30 +288,30 @@ namespace { }; template <> - struct TTypeTraitsExpected<size_t>: public TTypeTraitsExpected<int> { + struct TTypeTraitsExpected<size_t>: public TTypeTraitsExpected<int> { }; template <> - struct TTypeTraitsExpected<float>: public TTypeTraitsExpected<int> { + struct TTypeTraitsExpected<float>: public TTypeTraitsExpected<int> { enum { IsIntegral = false }; }; template <> - struct TTypeTraitsExpected<long double>: public TTypeTraitsExpected<float> { + struct TTypeTraitsExpected<long double>: public TTypeTraitsExpected<float> { }; template <> - struct TTypeTraitsExpected<const int>: public TTypeTraitsExpected<int> { + struct TTypeTraitsExpected<const int>: public TTypeTraitsExpected<int> { enum { IsConstant = true }; }; template <> - struct TTypeTraitsExpected<volatile int>: public TTypeTraitsExpected<int> { + struct TTypeTraitsExpected<volatile int>: public TTypeTraitsExpected<int> { enum { IsVolatile = true }; }; template <> - struct TTypeTraitsExpected<ETestEnum>: public TTypeTraitsExpected<int> { + struct TTypeTraitsExpected<ETestEnum>: public TTypeTraitsExpected<int> { enum { IsIntegral = false }; enum { IsArithmetic = false }; enum { IsEnum = true }; @@ -335,7 +335,7 @@ namespace { enum { IsLvalueReference = true }; }; - template <> + template <> struct TTypeTraitsExpected<TNonPodClass&&>: public TTypeTraitsExpected<TNonPodClass> { enum { IsClassType = false }; enum { IsReference = true }; @@ -347,39 +347,39 @@ namespace { }; template <> - struct TTypeTraitsExpected<float*>: public TTypeTraitsExpected<int> { + struct TTypeTraitsExpected<float*>: public TTypeTraitsExpected<int> { enum { IsIntegral = false }; enum { IsArithmetic = false }; enum { IsPointer = true }; }; template <> - struct TTypeTraitsExpected<float&>: public TTypeTraitsExpected<float*> { + struct TTypeTraitsExpected<float&>: public TTypeTraitsExpected<float*> { enum { IsPointer = false }; enum { IsReference = true }; enum { IsLvalueReference = true }; }; template <> - struct TTypeTraitsExpected<float&&>: public TTypeTraitsExpected<float*> { + struct TTypeTraitsExpected<float&&>: public TTypeTraitsExpected<float*> { enum { IsPointer = false }; enum { IsReference = true }; enum { IsRvalueReference = true }; }; template <> - struct TTypeTraitsExpected<const float&>: public TTypeTraitsExpected<float&> { + struct TTypeTraitsExpected<const float&>: public TTypeTraitsExpected<float&> { }; template <> - struct TTypeTraitsExpected<float[17]>: public TTypeTraitsExpected<int> { + struct TTypeTraitsExpected<float[17]>: public TTypeTraitsExpected<int> { enum { IsIntegral = false }; enum { IsArithmetic = false }; enum { IsArray = true }; }; } -#define UNIT_ASSERT_EQUAL_ENUM(expected, actual) UNIT_ASSERT_VALUES_EQUAL((bool)(expected), (bool)(actual)) +#define UNIT_ASSERT_EQUAL_ENUM(expected, actual) UNIT_ASSERT_VALUES_EQUAL((bool)(expected), (bool)(actual)) Y_UNIT_TEST_SUITE(TTypeTraitsTestNg) { template <typename T> @@ -399,10 +399,10 @@ Y_UNIT_TEST_SUITE(TTypeTraitsTestNg) { UNIT_ASSERT_EQUAL_ENUM(TTypeTraitsExpected<T>::IsClassType, std::is_class<T>::value); } -#define TYPE_TEST(name, type) \ - Y_UNIT_TEST(name) { \ - TestImpl<type>(); \ - } +#define TYPE_TEST(name, type) \ + Y_UNIT_TEST(name) { \ + TestImpl<type>(); \ + } TYPE_TEST(Void, void) TYPE_TEST(Int, int) @@ -426,11 +426,11 @@ enum E4 { X }; -enum class E64: ui64 { +enum class E64: ui64 { X }; -enum class E8: ui8 { +enum class E8: ui8 { X }; diff --git a/util/generic/ut/ya.make b/util/generic/ut/ya.make index cd28d47a52..6eaf24cc5f 100644 --- a/util/generic/ut/ya.make +++ b/util/generic/ut/ya.make @@ -1,4 +1,4 @@ -UNITTEST_FOR(util) +UNITTEST_FOR(util) OWNER(g:util) SUBSCRIBER(g:util-subscribers) @@ -6,54 +6,54 @@ SUBSCRIBER(g:util-subscribers) FORK_TESTS() SRCS( - generic/adaptor_ut.cpp + generic/adaptor_ut.cpp generic/algorithm_ut.cpp generic/array_ref_ut.cpp - generic/array_size_ut.cpp - generic/bitmap_ut.cpp - generic/bitops_ut.cpp - generic/buffer_ut.cpp - generic/cast_ut.cpp - generic/deque_ut.cpp - generic/explicit_type_ut.cpp + generic/array_size_ut.cpp + generic/bitmap_ut.cpp + generic/bitops_ut.cpp + generic/buffer_ut.cpp + generic/cast_ut.cpp + generic/deque_ut.cpp + generic/explicit_type_ut.cpp generic/flags_ut.cpp - generic/function_ut.cpp - generic/guid_ut.cpp + generic/function_ut.cpp + generic/guid_ut.cpp generic/hash_primes_ut.cpp - generic/hash_ut.cpp - generic/intrlist_ut.cpp - generic/is_in_ut.cpp - generic/iterator_ut.cpp + generic/hash_ut.cpp + generic/intrlist_ut.cpp + generic/is_in_ut.cpp + generic/iterator_ut.cpp generic/iterator_range_ut.cpp generic/lazy_value_ut.cpp - generic/list_ut.cpp - generic/map_ut.cpp - generic/mapfindptr_ut.cpp - generic/maybe_ut.cpp + generic/list_ut.cpp + generic/map_ut.cpp + generic/mapfindptr_ut.cpp + generic/maybe_ut.cpp generic/mem_copy_ut.cpp generic/objects_counter_ut.cpp generic/overloaded_ut.cpp - generic/ptr_ut.cpp - generic/queue_ut.cpp + generic/ptr_ut.cpp + generic/queue_ut.cpp generic/serialized_enum_ut.cpp - generic/set_ut.cpp + generic/set_ut.cpp generic/singleton_ut.cpp generic/size_literals_ut.cpp generic/stack_ut.cpp generic/store_policy_ut.cpp - generic/strbuf_ut.cpp + generic/strbuf_ut.cpp generic/string_ut.cpp generic/typelist_ut.cpp - generic/typetraits_ut.cpp - generic/utility_ut.cpp + generic/typetraits_ut.cpp + generic/utility_ut.cpp generic/va_args_ut.cpp - generic/vector_ut.cpp + generic/vector_ut.cpp generic/xrange_ut.cpp - generic/yexception_ut.c - generic/yexception_ut.cpp - generic/ylimits_ut.cpp - generic/ymath_ut.cpp - generic/scope_ut.cpp + generic/yexception_ut.c + generic/yexception_ut.cpp + generic/ylimits_ut.cpp + generic/ymath_ut.cpp + generic/scope_ut.cpp ) INCLUDE(${ARCADIA_ROOT}/util/tests/ya_util_tests.inc) diff --git a/util/generic/utility.cpp b/util/generic/utility.cpp index 146ba831dc..e1ed101c76 100644 --- a/util/generic/utility.cpp +++ b/util/generic/utility.cpp @@ -1,7 +1,7 @@ #include "utility.h" #ifdef _MSC_VER - #include <Windows.h> + #include <Windows.h> #endif void SecureZero(void* pointer, size_t count) noexcept { @@ -10,7 +10,7 @@ void SecureZero(void* pointer, size_t count) noexcept { #elif defined(memset_s) memset_s(pointer, count, 0, count); #else - volatile char* vPointer = (volatile char*)pointer; + volatile char* vPointer = (volatile char*)pointer; while (count) { *vPointer = 0; diff --git a/util/generic/utility.h b/util/generic/utility.h index 4e02f2db44..43b98eeafc 100644 --- a/util/generic/utility.h +++ b/util/generic/utility.h @@ -1,35 +1,35 @@ #pragma once - -#include "typetraits.h" - -#include <cstring> - -template <class T> + +#include "typetraits.h" + +#include <cstring> + +template <class T> static constexpr const T& Min(const T& l, const T& r) { return r < l ? r : l; -} - -template <typename T, typename... Args> +} + +template <typename T, typename... Args> static constexpr const T& Min(const T& a, const T& b, const Args&... args) { return Min(a, Min(b, args...)); } -template <class T> +template <class T> static constexpr const T& Max(const T& l, const T& r) { return l < r ? r : l; -} - -template <typename T, typename... Args> +} + +template <typename T, typename... Args> static constexpr const T& Max(const T& a, const T& b, const Args&... args) { return Max(a, Max(b, args...)); } // replace with http://en.cppreference.com/w/cpp/algorithm/clamp in c++17 -template <class T> +template <class T> constexpr const T& ClampVal(const T& val, const T& min, const T& max) { return val < min ? min : (max < val ? max : val); -} - +} + template <typename T = double, typename... Args> static T Mean(const Args&... other) noexcept { const auto numArgs = sizeof...(other); @@ -42,11 +42,11 @@ static T Mean(const Args&... other) noexcept { return sum / numArgs; } -template <class T> +template <class T> static inline void Zero(T& t) noexcept { memset((void*)&t, 0, sizeof(t)); -} - +} + /** * Securely zero memory (compiler does not optimize this out) * @@ -65,10 +65,10 @@ static inline void SecureZero(T& t) noexcept { SecureZero((void*)&t, sizeof(t)); } -namespace NSwapCheck { +namespace NSwapCheck { Y_HAS_MEMBER(swap); Y_HAS_MEMBER(Swap); - + template <class T, class = void> struct TSwapSelector { static inline void Swap(T& l, T& r) noexcept(std::is_nothrow_move_constructible<T>::value&& @@ -76,40 +76,40 @@ namespace NSwapCheck { T tmp(std::move(l)); l = std::move(r); r = std::move(tmp); - } - }; - + } + }; + template <class T> struct TSwapSelector<T, std::enable_if_t<THasSwap<T>::value>> { static inline void Swap(T& l, T& r) noexcept(noexcept(l.Swap(r))) { l.Swap(r); - } - }; - + } + }; + template <class T> struct TSwapSelector<T, std::enable_if_t<THasswap<T>::value && !THasSwap<T>::value>> { static inline void Swap(T& l, T& r) noexcept(noexcept(l.swap(r))) { l.swap(r); - } - }; -} - -/* - * DoSwap better than ::Swap in member functions... - */ -template <class T> + } + }; +} + +/* + * DoSwap better than ::Swap in member functions... + */ +template <class T> static inline void DoSwap(T& l, T& r) noexcept(noexcept(NSwapCheck::TSwapSelector<T>::Swap(l, r))) { - NSwapCheck::TSwapSelector<T>::Swap(l, r); -} + NSwapCheck::TSwapSelector<T>::Swap(l, r); +} template <bool b> struct TNullTmpl { - template <class T> + template <class T> operator T() const { return (T)0; } }; - + using TNull = TNullTmpl<0>; /* diff --git a/util/generic/utility_ut.cpp b/util/generic/utility_ut.cpp index 2524ecdc63..8e9d5afff9 100644 --- a/util/generic/utility_ut.cpp +++ b/util/generic/utility_ut.cpp @@ -1,180 +1,180 @@ -#include "utility.h" +#include "utility.h" #include "ymath.h" - + #include <library/cpp/testing/unittest/registar.h> - -// DO_NOT_STYLE - + +// DO_NOT_STYLE + class TTest { public: inline TTest(int val) : Val(val) { } - + inline void Swap(TTest& t) { DoSwap(Val, t.Val); } - + int Val; - + private: TTest(const TTest&); TTest& operator=(const TTest&); }; - + struct TUnorderedTag { TStringBuf Tag; }; - + static bool operator<(const TUnorderedTag, const TUnorderedTag) { return false; } static bool operator>(const TUnorderedTag, const TUnorderedTag) = delete; -Y_UNIT_TEST_SUITE(TUtilityTest) { - - Y_UNIT_TEST(TestSwapPrimitive) { - int i = 0; - int j = 1; - - DoSwap(i, j); - - UNIT_ASSERT_EQUAL(i, 1); - UNIT_ASSERT_EQUAL(j, 0); - } - - Y_UNIT_TEST(TestSwapClass) { - TTest i(0); - TTest j(1); - - DoSwap(i, j); - - UNIT_ASSERT_EQUAL(i.Val, 1); - UNIT_ASSERT_EQUAL(j.Val, 0); - } - - Y_UNIT_TEST(TestMaxMin) { - static_assert(Min(10, 3, 8) == 3, "Min doesn't work"); - static_assert(Max(10, 3, 8) == 10, "Max doesn't work"); - UNIT_ASSERT_EQUAL(Min(10, 3, 8), 3); - UNIT_ASSERT_EQUAL(Max(3.5, 4.2, 8.1, 99.025, 0.33, 29.0), 99.025); - - UNIT_ASSERT_VALUES_EQUAL(Min(TUnorderedTag{"first"}, TUnorderedTag{"second"}).Tag, "first"); - UNIT_ASSERT_VALUES_EQUAL(Max(TUnorderedTag{"first"}, TUnorderedTag{"second"}).Tag, "first"); - UNIT_ASSERT_VALUES_EQUAL(Min(TUnorderedTag{"first"}, TUnorderedTag{"second"}, TUnorderedTag{"third"}).Tag, "first"); - UNIT_ASSERT_VALUES_EQUAL(Max(TUnorderedTag{"first"}, TUnorderedTag{"second"}, TUnorderedTag{"third"}).Tag, "first"); - } - - Y_UNIT_TEST(TestMean) { - UNIT_ASSERT_EQUAL(Mean(5), 5); - UNIT_ASSERT_EQUAL(Mean(1, 2, 3), 2); - UNIT_ASSERT_EQUAL(Mean(6, 5, 4), 5); - UNIT_ASSERT_EQUAL(Mean(1, 2), 1.5); - UNIT_ASSERT(Abs(Mean(1., 2., 7.5) - 3.5) < std::numeric_limits<double>::epsilon()); - } - - Y_UNIT_TEST(TestZeroInitWithDefaultZeros) { - struct TStructWithPaddingBytes: public TZeroInit<TStructWithPaddingBytes> { - TStructWithPaddingBytes() - : TZeroInit<TStructWithPaddingBytes>() { - } - bool Field1_ = static_cast<bool>(0); - // here between Field1_ and Field2_ will be padding bytes - i64 Field2_ = 0; - }; - - TStructWithPaddingBytes foo{}; - - // all bytes must be zeroes, and MSAN will not complain about reading from padding bytes - const char* const fooPtr = (char*)&foo; - for (size_t i = 0; i < sizeof(TStructWithPaddingBytes); ++i) { - const char byte = fooPtr[i]; - UNIT_ASSERT_EQUAL(byte, 0); - } +Y_UNIT_TEST_SUITE(TUtilityTest) { + + Y_UNIT_TEST(TestSwapPrimitive) { + int i = 0; + int j = 1; + + DoSwap(i, j); + + UNIT_ASSERT_EQUAL(i, 1); + UNIT_ASSERT_EQUAL(j, 0); + } + + Y_UNIT_TEST(TestSwapClass) { + TTest i(0); + TTest j(1); + + DoSwap(i, j); + + UNIT_ASSERT_EQUAL(i.Val, 1); + UNIT_ASSERT_EQUAL(j.Val, 0); + } + + Y_UNIT_TEST(TestMaxMin) { + static_assert(Min(10, 3, 8) == 3, "Min doesn't work"); + static_assert(Max(10, 3, 8) == 10, "Max doesn't work"); + UNIT_ASSERT_EQUAL(Min(10, 3, 8), 3); + UNIT_ASSERT_EQUAL(Max(3.5, 4.2, 8.1, 99.025, 0.33, 29.0), 99.025); + + UNIT_ASSERT_VALUES_EQUAL(Min(TUnorderedTag{"first"}, TUnorderedTag{"second"}).Tag, "first"); + UNIT_ASSERT_VALUES_EQUAL(Max(TUnorderedTag{"first"}, TUnorderedTag{"second"}).Tag, "first"); + UNIT_ASSERT_VALUES_EQUAL(Min(TUnorderedTag{"first"}, TUnorderedTag{"second"}, TUnorderedTag{"third"}).Tag, "first"); + UNIT_ASSERT_VALUES_EQUAL(Max(TUnorderedTag{"first"}, TUnorderedTag{"second"}, TUnorderedTag{"third"}).Tag, "first"); + } + + Y_UNIT_TEST(TestMean) { + UNIT_ASSERT_EQUAL(Mean(5), 5); + UNIT_ASSERT_EQUAL(Mean(1, 2, 3), 2); + UNIT_ASSERT_EQUAL(Mean(6, 5, 4), 5); + UNIT_ASSERT_EQUAL(Mean(1, 2), 1.5); + UNIT_ASSERT(Abs(Mean(1., 2., 7.5) - 3.5) < std::numeric_limits<double>::epsilon()); + } + + Y_UNIT_TEST(TestZeroInitWithDefaultZeros) { + struct TStructWithPaddingBytes: public TZeroInit<TStructWithPaddingBytes> { + TStructWithPaddingBytes() + : TZeroInit<TStructWithPaddingBytes>() { + } + bool Field1_ = static_cast<bool>(0); + // here between Field1_ and Field2_ will be padding bytes + i64 Field2_ = 0; + }; + + TStructWithPaddingBytes foo{}; + + // all bytes must be zeroes, and MSAN will not complain about reading from padding bytes + const char* const fooPtr = (char*)&foo; + for (size_t i = 0; i < sizeof(TStructWithPaddingBytes); ++i) { + const char byte = fooPtr[i]; + UNIT_ASSERT_EQUAL(byte, 0); + } + } + + Y_UNIT_TEST(TestZeroInitWithDefaultNonZeros) { + struct TStructWithPaddingBytes: public TZeroInit<TStructWithPaddingBytes> { + TStructWithPaddingBytes() + : TZeroInit<TStructWithPaddingBytes>() { + } + bool Field1_ = true; + // here between Field1_ and Field2_ will be padding bytes + i64 Field2_ = 100500; + }; + + TStructWithPaddingBytes foo{}; + + // check that default values are set correctly + UNIT_ASSERT_EQUAL(foo.Field1_, true); + UNIT_ASSERT_EQUAL(foo.Field2_, 100500); + + const char* const fooPtr = (char*)&foo; + // just reading all bytes, and MSAN must not complain about reading padding bytes + for (size_t i = 0; i < sizeof(TStructWithPaddingBytes); ++i) { + const char byte = fooPtr[i]; + UNIT_ASSERT_EQUAL(byte, byte); + } } - Y_UNIT_TEST(TestZeroInitWithDefaultNonZeros) { - struct TStructWithPaddingBytes: public TZeroInit<TStructWithPaddingBytes> { - TStructWithPaddingBytes() - : TZeroInit<TStructWithPaddingBytes>() { - } - bool Field1_ = true; - // here between Field1_ and Field2_ will be padding bytes - i64 Field2_ = 100500; - }; - - TStructWithPaddingBytes foo{}; - - // check that default values are set correctly - UNIT_ASSERT_EQUAL(foo.Field1_, true); - UNIT_ASSERT_EQUAL(foo.Field2_, 100500); - - const char* const fooPtr = (char*)&foo; - // just reading all bytes, and MSAN must not complain about reading padding bytes - for (size_t i = 0; i < sizeof(TStructWithPaddingBytes); ++i) { - const char byte = fooPtr[i]; - UNIT_ASSERT_EQUAL(byte, byte); - } + Y_UNIT_TEST(TestClampValNoClamp) { + double val = 2; + double lo = 1; + double hi = 3; + const double& clamped = ClampVal(val, lo, hi); + UNIT_ASSERT_EQUAL(clamped, val); + UNIT_ASSERT_EQUAL(&clamped, &val); } - Y_UNIT_TEST(TestClampValNoClamp) { - double val = 2; - double lo = 1; - double hi = 3; - const double& clamped = ClampVal(val, lo, hi); - UNIT_ASSERT_EQUAL(clamped, val); - UNIT_ASSERT_EQUAL(&clamped, &val); - } - - Y_UNIT_TEST(TestClampValLo) { - double val = 2; - double lo = 3; - double hi = 4; - const double& clamped = ClampVal(val, lo, hi); - UNIT_ASSERT_EQUAL(clamped, lo); - UNIT_ASSERT_EQUAL(&clamped, &lo); - } - - Y_UNIT_TEST(TestClampValHi) { - double val = 4; - double lo = 3; - double hi = 2; - const double& clamped = ClampVal(val, lo, hi); - UNIT_ASSERT_EQUAL(clamped, hi); - UNIT_ASSERT_EQUAL(&clamped, &hi); - } - - Y_UNIT_TEST(TestSecureZero) { - constexpr size_t checkSize = 128; - char test[checkSize]; - - // fill with garbage - for (size_t i = 0; i < checkSize; ++i) { - test[i] = i; - } - - SecureZero(test, checkSize); - - for (size_t i = 0; i < checkSize; ++i) { - UNIT_ASSERT_EQUAL(test[i], 0); - } + Y_UNIT_TEST(TestClampValLo) { + double val = 2; + double lo = 3; + double hi = 4; + const double& clamped = ClampVal(val, lo, hi); + UNIT_ASSERT_EQUAL(clamped, lo); + UNIT_ASSERT_EQUAL(&clamped, &lo); } - Y_UNIT_TEST(TestSecureZeroTemplate) { - constexpr size_t checkSize = 128; - char test[checkSize]; + Y_UNIT_TEST(TestClampValHi) { + double val = 4; + double lo = 3; + double hi = 2; + const double& clamped = ClampVal(val, lo, hi); + UNIT_ASSERT_EQUAL(clamped, hi); + UNIT_ASSERT_EQUAL(&clamped, &hi); + } + + Y_UNIT_TEST(TestSecureZero) { + constexpr size_t checkSize = 128; + char test[checkSize]; + + // fill with garbage + for (size_t i = 0; i < checkSize; ++i) { + test[i] = i; + } + + SecureZero(test, checkSize); - // fill with garbage - for (size_t i = 0; i < checkSize; ++i) { - test[i] = i; - } + for (size_t i = 0; i < checkSize; ++i) { + UNIT_ASSERT_EQUAL(test[i], 0); + } + } + + Y_UNIT_TEST(TestSecureZeroTemplate) { + constexpr size_t checkSize = 128; + char test[checkSize]; - SecureZero(test); + // fill with garbage + for (size_t i = 0; i < checkSize; ++i) { + test[i] = i; + } - for (size_t i = 0; i < checkSize; ++i) { - UNIT_ASSERT_EQUAL(test[i], 0); - } + SecureZero(test); + + for (size_t i = 0; i < checkSize; ++i) { + UNIT_ASSERT_EQUAL(test[i], 0); + } } -}; +}; diff --git a/util/generic/va_args.cpp b/util/generic/va_args.cpp index 62694bcee3..2266d05a0d 100644 --- a/util/generic/va_args.cpp +++ b/util/generic/va_args.cpp @@ -5,11 +5,11 @@ Y_MAP_ARGS(__DUMMY__, 1, 2, 3); #define __DUMMY_LAST__(x) Y_MAP_ARGS_WITH_LAST(__DUMMY__, __DUMMY_LAST__, 1, 2, 3); -#undef __DUMMY_LAST__ -#undef __DUMMY__ +#undef __DUMMY_LAST__ +#undef __DUMMY__ #define __MULTI_DUMMY__(x, y) #define __MULTI_DUMMY_PROXY__(x) __MULTI_DUMMY__ x Y_MAP_ARGS(__MULTI_DUMMY_PROXY__, (1, 2), (3, 4)); -#undef __MULTI_DUMMY_PROXY__ -#undef __MULTI_DUMMY__ +#undef __MULTI_DUMMY_PROXY__ +#undef __MULTI_DUMMY__ diff --git a/util/generic/va_args.h b/util/generic/va_args.h index a80347be79..33498d47ed 100644 --- a/util/generic/va_args.h +++ b/util/generic/va_args.h @@ -88,153 +88,153 @@ #define Y_MAP_ARGS(ACTION, ...) Y_PASS_VA_ARGS(Y_PASS_VA_ARGS(Y_CAT(__Y_MAP_ARGS_, Y_COUNT_ARGS(__VA_ARGS__)))(ACTION, __VA_ARGS__)) #define __Y_MAP_ARGS_0(...) #define __Y_MAP_ARGS_1(ACTION, x, ...) ACTION(x) -#define __Y_MAP_ARGS_2(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_1(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_3(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_2(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_4(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_3(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_5(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_4(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_6(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_5(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_7(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_6(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_8(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_7(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_9(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_8(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_10(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_9(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_11(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_10(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_12(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_11(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_13(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_12(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_14(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_13(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_15(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_14(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_16(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_15(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_17(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_16(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_18(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_17(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_19(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_18(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_20(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_19(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_21(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_20(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_22(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_21(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_23(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_22(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_24(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_23(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_25(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_24(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_26(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_25(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_27(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_26(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_28(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_27(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_29(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_28(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_30(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_29(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_31(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_30(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_32(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_31(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_33(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_32(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_34(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_33(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_35(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_34(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_36(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_35(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_37(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_36(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_38(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_37(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_39(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_38(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_40(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_39(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_41(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_40(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_42(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_41(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_43(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_42(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_44(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_43(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_45(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_44(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_46(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_45(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_47(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_46(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_48(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_47(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_49(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_48(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_50(ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_49(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_2(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_1(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_3(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_2(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_4(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_3(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_5(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_4(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_6(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_5(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_7(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_6(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_8(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_7(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_9(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_8(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_10(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_9(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_11(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_10(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_12(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_11(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_13(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_12(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_14(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_13(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_15(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_14(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_16(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_15(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_17(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_16(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_18(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_17(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_19(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_18(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_20(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_19(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_21(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_20(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_22(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_21(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_23(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_22(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_24(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_23(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_25(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_24(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_26(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_25(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_27(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_26(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_28(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_27(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_29(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_28(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_30(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_29(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_31(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_30(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_32(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_31(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_33(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_32(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_34(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_33(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_35(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_34(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_36(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_35(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_37(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_36(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_38(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_37(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_39(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_38(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_40(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_39(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_41(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_40(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_42(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_41(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_43(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_42(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_44(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_43(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_45(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_44(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_46(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_45(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_47(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_46(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_48(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_47(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_49(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_48(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_50(ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_49(ACTION, __VA_ARGS__)) /** * Expands a macro for each of the variable arguments with it's sequence number and value. @@ -244,153 +244,153 @@ #define Y_MAP_ARGS_N(ACTION, ...) Y_PASS_VA_ARGS(Y_PASS_VA_ARGS(Y_CAT(__Y_MAP_ARGS_N_, Y_COUNT_ARGS(__VA_ARGS__)))(ACTION, __VA_ARGS__)) #define __Y_MAP_ARGS_N_0(...) #define __Y_MAP_ARGS_N_1(ACTION, x, ...) ACTION(1, x) -#define __Y_MAP_ARGS_N_2(ACTION, x, ...) \ - ACTION(2, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_1(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_3(ACTION, x, ...) \ - ACTION(3, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_2(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_4(ACTION, x, ...) \ - ACTION(4, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_3(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_5(ACTION, x, ...) \ - ACTION(5, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_4(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_6(ACTION, x, ...) \ - ACTION(6, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_5(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_7(ACTION, x, ...) \ - ACTION(7, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_6(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_8(ACTION, x, ...) \ - ACTION(8, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_7(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_9(ACTION, x, ...) \ - ACTION(9, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_8(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_10(ACTION, x, ...) \ - ACTION(10, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_9(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_11(ACTION, x, ...) \ - ACTION(11, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_10(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_12(ACTION, x, ...) \ - ACTION(12, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_11(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_13(ACTION, x, ...) \ - ACTION(13, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_12(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_14(ACTION, x, ...) \ - ACTION(14, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_13(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_15(ACTION, x, ...) \ - ACTION(15, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_14(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_16(ACTION, x, ...) \ - ACTION(16, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_15(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_17(ACTION, x, ...) \ - ACTION(17, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_16(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_18(ACTION, x, ...) \ - ACTION(18, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_17(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_19(ACTION, x, ...) \ - ACTION(19, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_18(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_20(ACTION, x, ...) \ - ACTION(20, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_19(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_21(ACTION, x, ...) \ - ACTION(21, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_20(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_22(ACTION, x, ...) \ - ACTION(22, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_21(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_23(ACTION, x, ...) \ - ACTION(23, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_22(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_24(ACTION, x, ...) \ - ACTION(24, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_23(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_25(ACTION, x, ...) \ - ACTION(25, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_24(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_26(ACTION, x, ...) \ - ACTION(26, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_25(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_27(ACTION, x, ...) \ - ACTION(27, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_26(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_28(ACTION, x, ...) \ - ACTION(28, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_27(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_29(ACTION, x, ...) \ - ACTION(29, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_28(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_30(ACTION, x, ...) \ - ACTION(30, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_29(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_31(ACTION, x, ...) \ - ACTION(31, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_30(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_32(ACTION, x, ...) \ - ACTION(32, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_31(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_33(ACTION, x, ...) \ - ACTION(33, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_32(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_34(ACTION, x, ...) \ - ACTION(34, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_33(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_35(ACTION, x, ...) \ - ACTION(35, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_34(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_36(ACTION, x, ...) \ - ACTION(36, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_35(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_37(ACTION, x, ...) \ - ACTION(37, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_36(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_38(ACTION, x, ...) \ - ACTION(38, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_37(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_39(ACTION, x, ...) \ - ACTION(39, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_38(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_40(ACTION, x, ...) \ - ACTION(40, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_39(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_41(ACTION, x, ...) \ - ACTION(41, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_40(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_42(ACTION, x, ...) \ - ACTION(42, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_41(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_43(ACTION, x, ...) \ - ACTION(43, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_42(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_44(ACTION, x, ...) \ - ACTION(44, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_43(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_45(ACTION, x, ...) \ - ACTION(45, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_44(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_46(ACTION, x, ...) \ - ACTION(46, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_45(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_47(ACTION, x, ...) \ - ACTION(47, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_46(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_48(ACTION, x, ...) \ - ACTION(48, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_47(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_49(ACTION, x, ...) \ - ACTION(49, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_48(ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_N_50(ACTION, x, ...) \ - ACTION(50, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_49(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_2(ACTION, x, ...) \ + ACTION(2, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_1(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_3(ACTION, x, ...) \ + ACTION(3, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_2(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_4(ACTION, x, ...) \ + ACTION(4, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_3(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_5(ACTION, x, ...) \ + ACTION(5, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_4(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_6(ACTION, x, ...) \ + ACTION(6, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_5(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_7(ACTION, x, ...) \ + ACTION(7, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_6(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_8(ACTION, x, ...) \ + ACTION(8, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_7(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_9(ACTION, x, ...) \ + ACTION(9, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_8(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_10(ACTION, x, ...) \ + ACTION(10, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_9(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_11(ACTION, x, ...) \ + ACTION(11, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_10(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_12(ACTION, x, ...) \ + ACTION(12, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_11(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_13(ACTION, x, ...) \ + ACTION(13, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_12(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_14(ACTION, x, ...) \ + ACTION(14, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_13(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_15(ACTION, x, ...) \ + ACTION(15, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_14(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_16(ACTION, x, ...) \ + ACTION(16, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_15(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_17(ACTION, x, ...) \ + ACTION(17, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_16(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_18(ACTION, x, ...) \ + ACTION(18, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_17(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_19(ACTION, x, ...) \ + ACTION(19, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_18(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_20(ACTION, x, ...) \ + ACTION(20, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_19(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_21(ACTION, x, ...) \ + ACTION(21, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_20(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_22(ACTION, x, ...) \ + ACTION(22, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_21(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_23(ACTION, x, ...) \ + ACTION(23, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_22(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_24(ACTION, x, ...) \ + ACTION(24, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_23(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_25(ACTION, x, ...) \ + ACTION(25, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_24(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_26(ACTION, x, ...) \ + ACTION(26, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_25(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_27(ACTION, x, ...) \ + ACTION(27, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_26(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_28(ACTION, x, ...) \ + ACTION(28, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_27(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_29(ACTION, x, ...) \ + ACTION(29, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_28(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_30(ACTION, x, ...) \ + ACTION(30, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_29(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_31(ACTION, x, ...) \ + ACTION(31, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_30(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_32(ACTION, x, ...) \ + ACTION(32, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_31(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_33(ACTION, x, ...) \ + ACTION(33, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_32(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_34(ACTION, x, ...) \ + ACTION(34, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_33(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_35(ACTION, x, ...) \ + ACTION(35, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_34(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_36(ACTION, x, ...) \ + ACTION(36, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_35(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_37(ACTION, x, ...) \ + ACTION(37, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_36(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_38(ACTION, x, ...) \ + ACTION(38, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_37(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_39(ACTION, x, ...) \ + ACTION(39, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_38(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_40(ACTION, x, ...) \ + ACTION(40, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_39(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_41(ACTION, x, ...) \ + ACTION(41, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_40(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_42(ACTION, x, ...) \ + ACTION(42, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_41(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_43(ACTION, x, ...) \ + ACTION(43, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_42(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_44(ACTION, x, ...) \ + ACTION(44, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_43(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_45(ACTION, x, ...) \ + ACTION(45, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_44(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_46(ACTION, x, ...) \ + ACTION(46, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_45(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_47(ACTION, x, ...) \ + ACTION(47, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_46(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_48(ACTION, x, ...) \ + ACTION(48, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_47(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_49(ACTION, x, ...) \ + ACTION(49, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_48(ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_N_50(ACTION, x, ...) \ + ACTION(50, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_N_49(ACTION, __VA_ARGS__)) /** * Expands a macro for each of the variable arguments. @@ -399,153 +399,153 @@ #define Y_MAP_ARGS_WITH_LAST(ACTION, LAST_ACTION, ...) Y_PASS_VA_ARGS(Y_PASS_VA_ARGS(Y_CAT(__Y_MAP_ARGS_WITH_LAST_, Y_COUNT_ARGS(__VA_ARGS__)))(ACTION, LAST_ACTION, __VA_ARGS__)) #define __Y_MAP_ARGS_WITH_LAST_0(...) #define __Y_MAP_ARGS_WITH_LAST_1(ACTION, LAST_ACTION, x, ...) LAST_ACTION(x) -#define __Y_MAP_ARGS_WITH_LAST_2(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_1(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_3(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_2(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_4(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_3(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_5(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_4(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_6(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_5(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_7(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_6(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_8(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_7(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_9(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_8(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_10(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_9(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_11(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_10(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_12(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_11(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_13(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_12(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_14(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_13(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_15(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_14(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_16(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_15(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_17(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_16(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_18(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_17(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_19(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_18(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_20(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_19(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_21(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_20(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_22(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_21(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_23(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_22(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_24(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_23(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_25(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_24(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_26(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_25(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_27(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_26(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_28(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_27(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_29(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_28(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_30(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_29(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_31(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_30(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_32(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_31(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_33(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_32(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_34(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_33(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_35(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_34(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_36(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_35(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_37(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_36(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_38(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_37(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_39(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_38(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_40(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_39(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_41(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_40(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_42(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_41(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_43(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_42(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_44(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_43(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_45(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_44(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_46(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_45(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_47(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_46(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_48(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_47(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_49(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_48(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_50(ACTION, LAST_ACTION, x, ...) \ - ACTION(x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_49(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_2(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_1(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_3(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_2(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_4(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_3(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_5(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_4(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_6(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_5(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_7(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_6(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_8(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_7(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_9(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_8(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_10(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_9(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_11(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_10(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_12(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_11(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_13(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_12(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_14(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_13(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_15(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_14(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_16(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_15(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_17(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_16(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_18(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_17(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_19(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_18(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_20(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_19(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_21(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_20(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_22(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_21(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_23(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_22(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_24(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_23(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_25(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_24(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_26(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_25(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_27(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_26(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_28(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_27(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_29(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_28(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_30(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_29(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_31(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_30(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_32(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_31(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_33(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_32(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_34(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_33(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_35(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_34(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_36(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_35(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_37(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_36(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_38(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_37(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_39(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_38(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_40(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_39(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_41(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_40(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_42(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_41(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_43(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_42(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_44(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_43(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_45(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_44(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_46(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_45(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_47(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_46(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_48(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_47(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_49(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_48(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_50(ACTION, LAST_ACTION, x, ...) \ + ACTION(x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_49(ACTION, LAST_ACTION, __VA_ARGS__)) /** * Expands a macro for each of the variable arguments with it's sequence number and value. @@ -555,153 +555,153 @@ #define Y_MAP_ARGS_WITH_LAST_N(ACTION, LAST_ACTION, ...) Y_PASS_VA_ARGS(Y_PASS_VA_ARGS(Y_CAT(__Y_MAP_ARGS_WITH_LAST_N_, Y_COUNT_ARGS(__VA_ARGS__)))(ACTION, LAST_ACTION, __VA_ARGS__)) #define __Y_MAP_ARGS_WITH_LAST_N_0(...) #define __Y_MAP_ARGS_WITH_LAST_N_1(ACTION, LAST_ACTION, x, ...) LAST_ACTION(1, x) -#define __Y_MAP_ARGS_WITH_LAST_N_2(ACTION, LAST_ACTION, x, ...) \ - ACTION(2, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_1(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_3(ACTION, LAST_ACTION, x, ...) \ - ACTION(3, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_2(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_4(ACTION, LAST_ACTION, x, ...) \ - ACTION(4, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_3(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_5(ACTION, LAST_ACTION, x, ...) \ - ACTION(5, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_4(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_6(ACTION, LAST_ACTION, x, ...) \ - ACTION(6, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_5(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_7(ACTION, LAST_ACTION, x, ...) \ - ACTION(7, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_6(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_8(ACTION, LAST_ACTION, x, ...) \ - ACTION(8, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_7(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_9(ACTION, LAST_ACTION, x, ...) \ - ACTION(9, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_8(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_10(ACTION, LAST_ACTION, x, ...) \ - ACTION(10, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_9(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_11(ACTION, LAST_ACTION, x, ...) \ - ACTION(11, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_10(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_12(ACTION, LAST_ACTION, x, ...) \ - ACTION(12, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_11(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_13(ACTION, LAST_ACTION, x, ...) \ - ACTION(13, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_12(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_14(ACTION, LAST_ACTION, x, ...) \ - ACTION(14, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_13(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_15(ACTION, LAST_ACTION, x, ...) \ - ACTION(15, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_14(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_16(ACTION, LAST_ACTION, x, ...) \ - ACTION(16, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_15(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_17(ACTION, LAST_ACTION, x, ...) \ - ACTION(17, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_16(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_18(ACTION, LAST_ACTION, x, ...) \ - ACTION(18, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_17(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_19(ACTION, LAST_ACTION, x, ...) \ - ACTION(19, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_18(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_20(ACTION, LAST_ACTION, x, ...) \ - ACTION(20, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_19(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_21(ACTION, LAST_ACTION, x, ...) \ - ACTION(21, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_20(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_22(ACTION, LAST_ACTION, x, ...) \ - ACTION(22, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_21(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_23(ACTION, LAST_ACTION, x, ...) \ - ACTION(23, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_22(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_24(ACTION, LAST_ACTION, x, ...) \ - ACTION(24, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_23(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_25(ACTION, LAST_ACTION, x, ...) \ - ACTION(25, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_24(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_26(ACTION, LAST_ACTION, x, ...) \ - ACTION(26, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_25(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_27(ACTION, LAST_ACTION, x, ...) \ - ACTION(27, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_26(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_28(ACTION, LAST_ACTION, x, ...) \ - ACTION(28, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_27(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_29(ACTION, LAST_ACTION, x, ...) \ - ACTION(29, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_28(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_30(ACTION, LAST_ACTION, x, ...) \ - ACTION(30, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_29(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_31(ACTION, LAST_ACTION, x, ...) \ - ACTION(31, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_30(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_32(ACTION, LAST_ACTION, x, ...) \ - ACTION(32, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_31(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_33(ACTION, LAST_ACTION, x, ...) \ - ACTION(33, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_32(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_34(ACTION, LAST_ACTION, x, ...) \ - ACTION(34, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_33(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_35(ACTION, LAST_ACTION, x, ...) \ - ACTION(35, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_34(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_36(ACTION, LAST_ACTION, x, ...) \ - ACTION(36, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_35(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_37(ACTION, LAST_ACTION, x, ...) \ - ACTION(37, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_36(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_38(ACTION, LAST_ACTION, x, ...) \ - ACTION(38, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_37(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_39(ACTION, LAST_ACTION, x, ...) \ - ACTION(39, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_38(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_40(ACTION, LAST_ACTION, x, ...) \ - ACTION(40, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_39(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_41(ACTION, LAST_ACTION, x, ...) \ - ACTION(41, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_40(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_42(ACTION, LAST_ACTION, x, ...) \ - ACTION(42, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_41(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_43(ACTION, LAST_ACTION, x, ...) \ - ACTION(43, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_42(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_44(ACTION, LAST_ACTION, x, ...) \ - ACTION(44, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_43(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_45(ACTION, LAST_ACTION, x, ...) \ - ACTION(45, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_44(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_46(ACTION, LAST_ACTION, x, ...) \ - ACTION(46, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_45(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_47(ACTION, LAST_ACTION, x, ...) \ - ACTION(47, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_46(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_48(ACTION, LAST_ACTION, x, ...) \ - ACTION(48, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_47(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_49(ACTION, LAST_ACTION, x, ...) \ - ACTION(49, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_48(ACTION, LAST_ACTION, __VA_ARGS__)) -#define __Y_MAP_ARGS_WITH_LAST_N_50(ACTION, LAST_ACTION, x, ...) \ - ACTION(50, x) \ - Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_49(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_2(ACTION, LAST_ACTION, x, ...) \ + ACTION(2, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_1(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_3(ACTION, LAST_ACTION, x, ...) \ + ACTION(3, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_2(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_4(ACTION, LAST_ACTION, x, ...) \ + ACTION(4, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_3(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_5(ACTION, LAST_ACTION, x, ...) \ + ACTION(5, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_4(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_6(ACTION, LAST_ACTION, x, ...) \ + ACTION(6, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_5(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_7(ACTION, LAST_ACTION, x, ...) \ + ACTION(7, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_6(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_8(ACTION, LAST_ACTION, x, ...) \ + ACTION(8, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_7(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_9(ACTION, LAST_ACTION, x, ...) \ + ACTION(9, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_8(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_10(ACTION, LAST_ACTION, x, ...) \ + ACTION(10, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_9(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_11(ACTION, LAST_ACTION, x, ...) \ + ACTION(11, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_10(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_12(ACTION, LAST_ACTION, x, ...) \ + ACTION(12, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_11(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_13(ACTION, LAST_ACTION, x, ...) \ + ACTION(13, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_12(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_14(ACTION, LAST_ACTION, x, ...) \ + ACTION(14, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_13(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_15(ACTION, LAST_ACTION, x, ...) \ + ACTION(15, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_14(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_16(ACTION, LAST_ACTION, x, ...) \ + ACTION(16, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_15(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_17(ACTION, LAST_ACTION, x, ...) \ + ACTION(17, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_16(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_18(ACTION, LAST_ACTION, x, ...) \ + ACTION(18, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_17(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_19(ACTION, LAST_ACTION, x, ...) \ + ACTION(19, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_18(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_20(ACTION, LAST_ACTION, x, ...) \ + ACTION(20, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_19(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_21(ACTION, LAST_ACTION, x, ...) \ + ACTION(21, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_20(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_22(ACTION, LAST_ACTION, x, ...) \ + ACTION(22, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_21(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_23(ACTION, LAST_ACTION, x, ...) \ + ACTION(23, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_22(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_24(ACTION, LAST_ACTION, x, ...) \ + ACTION(24, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_23(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_25(ACTION, LAST_ACTION, x, ...) \ + ACTION(25, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_24(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_26(ACTION, LAST_ACTION, x, ...) \ + ACTION(26, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_25(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_27(ACTION, LAST_ACTION, x, ...) \ + ACTION(27, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_26(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_28(ACTION, LAST_ACTION, x, ...) \ + ACTION(28, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_27(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_29(ACTION, LAST_ACTION, x, ...) \ + ACTION(29, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_28(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_30(ACTION, LAST_ACTION, x, ...) \ + ACTION(30, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_29(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_31(ACTION, LAST_ACTION, x, ...) \ + ACTION(31, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_30(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_32(ACTION, LAST_ACTION, x, ...) \ + ACTION(32, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_31(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_33(ACTION, LAST_ACTION, x, ...) \ + ACTION(33, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_32(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_34(ACTION, LAST_ACTION, x, ...) \ + ACTION(34, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_33(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_35(ACTION, LAST_ACTION, x, ...) \ + ACTION(35, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_34(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_36(ACTION, LAST_ACTION, x, ...) \ + ACTION(36, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_35(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_37(ACTION, LAST_ACTION, x, ...) \ + ACTION(37, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_36(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_38(ACTION, LAST_ACTION, x, ...) \ + ACTION(38, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_37(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_39(ACTION, LAST_ACTION, x, ...) \ + ACTION(39, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_38(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_40(ACTION, LAST_ACTION, x, ...) \ + ACTION(40, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_39(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_41(ACTION, LAST_ACTION, x, ...) \ + ACTION(41, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_40(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_42(ACTION, LAST_ACTION, x, ...) \ + ACTION(42, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_41(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_43(ACTION, LAST_ACTION, x, ...) \ + ACTION(43, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_42(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_44(ACTION, LAST_ACTION, x, ...) \ + ACTION(44, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_43(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_45(ACTION, LAST_ACTION, x, ...) \ + ACTION(45, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_44(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_46(ACTION, LAST_ACTION, x, ...) \ + ACTION(46, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_45(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_47(ACTION, LAST_ACTION, x, ...) \ + ACTION(47, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_46(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_48(ACTION, LAST_ACTION, x, ...) \ + ACTION(48, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_47(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_49(ACTION, LAST_ACTION, x, ...) \ + ACTION(49, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_48(ACTION, LAST_ACTION, __VA_ARGS__)) +#define __Y_MAP_ARGS_WITH_LAST_N_50(ACTION, LAST_ACTION, x, ...) \ + ACTION(50, x) \ + Y_PASS_VA_ARGS(__Y_MAP_ARGS_WITH_LAST_N_49(ACTION, LAST_ACTION, __VA_ARGS__)) /** * Get all elements but the last one from `__VA_ARGS__`. @@ -764,7 +764,7 @@ * Get the last element from `__VA_ARGS__`. * Doesn't work with empty arguments list. */ -#define Y_LAST(...) Y_PASS_VA_ARGS(Y_GET_ARG(Y_COUNT_ARGS(__VA_ARGS__), , __VA_ARGS__, , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , )) +#define Y_LAST(...) Y_PASS_VA_ARGS(Y_GET_ARG(Y_COUNT_ARGS(__VA_ARGS__), , __VA_ARGS__, , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , )) /** * Macros for implementing overload by number of arguments. diff --git a/util/generic/va_args_ut.cpp b/util/generic/va_args_ut.cpp index 4044bb9a63..a9c96a0f55 100644 --- a/util/generic/va_args_ut.cpp +++ b/util/generic/va_args_ut.cpp @@ -13,8 +13,8 @@ Y_UNIT_TEST_SUITE(TMacroVarargMapTest) { #define ID(x) x static const int SUM = Y_MAP_ARGS_WITH_LAST(ADD, ID, 1, 2, 3, 4 + 5); UNIT_ASSERT_VALUES_EQUAL(SUM, 1 + 2 + 3 + 4 + 5); -#undef ADD -#undef ID +#undef ADD +#undef ID } Y_UNIT_TEST(TestMapArgsN) { @@ -42,65 +42,65 @@ Y_UNIT_TEST_SUITE(TMacroVarargMapTest) { } } -Y_UNIT_TEST_SUITE(TestVaArgs) { - Y_UNIT_TEST(Count) { +Y_UNIT_TEST_SUITE(TestVaArgs) { + Y_UNIT_TEST(Count) { // UNIT_ASSERT((Y_COUNT_ARGS() == 0)); // FIXME: make this case work after __VA_OPT__ (c++20) UNIT_ASSERT((Y_COUNT_ARGS(1) == 1)); - UNIT_ASSERT((Y_COUNT_ARGS(1, 2) == 2)); - UNIT_ASSERT((Y_COUNT_ARGS(1, 2, 3) == 3)); - UNIT_ASSERT((Y_COUNT_ARGS(1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0) == 20)); - } + UNIT_ASSERT((Y_COUNT_ARGS(1, 2) == 2)); + UNIT_ASSERT((Y_COUNT_ARGS(1, 2, 3) == 3)); + UNIT_ASSERT((Y_COUNT_ARGS(1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0) == 20)); + } - Y_UNIT_TEST(GetElem) { - UNIT_ASSERT((Y_GET_ARG(0, 1) == 1)); - UNIT_ASSERT((Y_GET_ARG(0, 0, 1, 2, 3, 4, 5) == 0)); - UNIT_ASSERT((Y_GET_ARG(1, 0, 1, 2, 3, 4, 5) == 1)); - UNIT_ASSERT((Y_GET_ARG(2, 0, 1, 2, 3, 4, 5) == 2)); - UNIT_ASSERT((Y_GET_ARG(3, 0, 1, 2, 3, 4, 5) == 3)); - UNIT_ASSERT((Y_GET_ARG(4, 0, 1, 2, 3, 4, 5) == 4)); - UNIT_ASSERT((Y_GET_ARG(5, 0, 1, 2, 3, 4, 5) == 5)); - } + Y_UNIT_TEST(GetElem) { + UNIT_ASSERT((Y_GET_ARG(0, 1) == 1)); + UNIT_ASSERT((Y_GET_ARG(0, 0, 1, 2, 3, 4, 5) == 0)); + UNIT_ASSERT((Y_GET_ARG(1, 0, 1, 2, 3, 4, 5) == 1)); + UNIT_ASSERT((Y_GET_ARG(2, 0, 1, 2, 3, 4, 5) == 2)); + UNIT_ASSERT((Y_GET_ARG(3, 0, 1, 2, 3, 4, 5) == 3)); + UNIT_ASSERT((Y_GET_ARG(4, 0, 1, 2, 3, 4, 5) == 4)); + UNIT_ASSERT((Y_GET_ARG(5, 0, 1, 2, 3, 4, 5) == 5)); + } - Y_UNIT_TEST(MapArgs) { + Y_UNIT_TEST(MapArgs) { #define MAP(x) x + /* NOLINT */ - // UNIT_ASSERT((Y_MAP_ARGS(MAP) 0 == 0)); // FIXME: make this case work after __VA_OPT__ (c++20) - UNIT_ASSERT((Y_MAP_ARGS(MAP, 1, 2, 3, 4) 0 == 10)); + // UNIT_ASSERT((Y_MAP_ARGS(MAP) 0 == 0)); // FIXME: make this case work after __VA_OPT__ (c++20) + UNIT_ASSERT((Y_MAP_ARGS(MAP, 1, 2, 3, 4) 0 == 10)); #undef MAP - } + } - Y_UNIT_TEST(MapArgsWithLast) { + Y_UNIT_TEST(MapArgsWithLast) { #define MAP(x) x + /* NOLINT */ #define MAP_LAST(x) x - UNIT_ASSERT((Y_MAP_ARGS_WITH_LAST(MAP, MAP_LAST, 1, 2, 3, 4) == 10)); + UNIT_ASSERT((Y_MAP_ARGS_WITH_LAST(MAP, MAP_LAST, 1, 2, 3, 4) == 10)); #undef MAP_LAST #undef MAP - } + } - Y_UNIT_TEST(AllButLast) { - const char array[] = {Y_ALL_BUT_LAST(1, 2, 3, 4, 5)}; - UNIT_ASSERT((sizeof(array) == 4)); - UNIT_ASSERT((array[0] == 1)); - UNIT_ASSERT((array[1] == 2)); - UNIT_ASSERT((array[2] == 3)); - UNIT_ASSERT((array[3] == 4)); - } + Y_UNIT_TEST(AllButLast) { + const char array[] = {Y_ALL_BUT_LAST(1, 2, 3, 4, 5)}; + UNIT_ASSERT((sizeof(array) == 4)); + UNIT_ASSERT((array[0] == 1)); + UNIT_ASSERT((array[1] == 2)); + UNIT_ASSERT((array[2] == 3)); + UNIT_ASSERT((array[3] == 4)); + } - Y_UNIT_TEST(Last) { - UNIT_ASSERT((Y_LAST(1) == 1)); - UNIT_ASSERT((Y_LAST(1, 2, 3) == 3)); - } + Y_UNIT_TEST(Last) { + UNIT_ASSERT((Y_LAST(1) == 1)); + UNIT_ASSERT((Y_LAST(1, 2, 3) == 3)); + } - Y_UNIT_TEST(ImplDispatcher) { + Y_UNIT_TEST(ImplDispatcher) { #define I1(x) (x) #define I2(x, y) ((x) + (y)) #define I3(x, y, z) ((x) + (y) + (z)) #define I(...) Y_PASS_VA_ARGS(Y_MACRO_IMPL_DISPATCHER_3(__VA_ARGS__, I3, I2, I1)(__VA_ARGS__)) - UNIT_ASSERT((I(1) == 1)); - UNIT_ASSERT((I(1, 2) == 3)); - UNIT_ASSERT((I(1, 2, 3) == 6)); + UNIT_ASSERT((I(1) == 1)); + UNIT_ASSERT((I(1, 2) == 3)); + UNIT_ASSERT((I(1, 2, 3) == 6)); #undef I #undef I3 #undef I2 #undef I1 - } -}; + } +}; diff --git a/util/generic/variant.cpp b/util/generic/variant.cpp index e82fee8749..1de3ade2ee 100644 --- a/util/generic/variant.cpp +++ b/util/generic/variant.cpp @@ -1 +1 @@ -#include "variant.h" +#include "variant.h" diff --git a/util/generic/variant.h b/util/generic/variant.h index e3d9d5ec92..749fc75090 100644 --- a/util/generic/variant.h +++ b/util/generic/variant.h @@ -18,6 +18,6 @@ template <> struct THash<std::monostate> { public: constexpr size_t operator()(std::monostate) const noexcept { - return 1; - } + return 1; + } }; diff --git a/util/generic/vector.cpp b/util/generic/vector.cpp index 5c6660f203..7da6cc5e86 100644 --- a/util/generic/vector.cpp +++ b/util/generic/vector.cpp @@ -1 +1 @@ -#include "vector.h" +#include "vector.h" diff --git a/util/generic/vector.h b/util/generic/vector.h index 2b81f9c4a9..a5b258955a 100644 --- a/util/generic/vector.h +++ b/util/generic/vector.h @@ -3,28 +3,28 @@ #include "fwd.h" #include "reserve.h" -#include <util/memory/alloc.h> - -#include <vector> +#include <util/memory/alloc.h> + +#include <vector> #include <initializer_list> - + template <class T, class A> class TVector: public std::vector<T, TReboundAllocator<A, T>> { -public: +public: using TBase = std::vector<T, TReboundAllocator<A, T>>; using TSelf = TVector<T, A>; using size_type = typename TBase::size_type; - + inline TVector() - : TBase() - { - } - + : TBase() + { + } + inline TVector(const typename TBase::allocator_type& a) - : TBase(a) - { - } - + : TBase(a) + { + } + inline explicit TVector(::NDetail::TReserveTag rt) : TBase() { @@ -38,20 +38,20 @@ public: } inline explicit TVector(size_type count) - : TBase(count) - { - } - + : TBase(count) + { + } + inline explicit TVector(size_type count, const typename TBase::allocator_type& a) : TBase(count, a) { } inline TVector(size_type count, const T& val) - : TBase(count, val) - { - } - + : TBase(count, val) + { + } + inline TVector(size_type count, const T& val, const typename TBase::allocator_type& a) : TBase(count, val, a) { @@ -69,20 +69,20 @@ public: inline TVector(const TSelf& src) : TBase(src) - { - } + { + } inline TVector(TSelf&& src) noexcept : TBase(std::forward<TSelf>(src)) { } - template <class TIter> + template <class TIter> inline TVector(TIter first, TIter last) - : TBase(first, last) - { - } - + : TBase(first, last) + { + } + inline TSelf& operator=(const TSelf& src) { TBase::operator=(src); return *this; @@ -98,17 +98,17 @@ public: return *this; } - inline explicit operator bool() const noexcept { + inline explicit operator bool() const noexcept { return !this->empty(); } - Y_PURE_FUNCTION inline bool empty() const noexcept { + Y_PURE_FUNCTION inline bool empty() const noexcept { return TBase::empty(); } inline yssize_t ysize() const noexcept { return (yssize_t)TBase::size(); - } + } #ifdef _YNDX_LIBCXX_ENABLE_VECTOR_POD_RESIZE_UNINITIALIZED void yresize(size_type newSize) { diff --git a/util/generic/vector.pxd b/util/generic/vector.pxd index 944c70ef17..99dde95d48 100644 --- a/util/generic/vector.pxd +++ b/util/generic/vector.pxd @@ -1,30 +1,30 @@ cdef extern from "<util/generic/vector.h>" nogil: cdef cppclass TVector[T]: - cppclass iterator: - T& operator*() - iterator operator++() - iterator operator--() - iterator operator+(size_t) - iterator operator-(size_t) - bint operator==(iterator) - bint operator!=(iterator) - bint operator<(iterator) - bint operator>(iterator) - bint operator<=(iterator) - bint operator>=(iterator) + cppclass iterator: + T& operator*() + iterator operator++() + iterator operator--() + iterator operator+(size_t) + iterator operator-(size_t) + bint operator==(iterator) + bint operator!=(iterator) + bint operator<(iterator) + bint operator>(iterator) + bint operator<=(iterator) + bint operator>=(iterator) - cppclass reverse_iterator: - T& operator*() + cppclass reverse_iterator: + T& operator*() reverse_iterator operator++() reverse_iterator operator--() reverse_iterator operator+(size_t) reverse_iterator operator-(size_t) - bint operator==(reverse_iterator) - bint operator!=(reverse_iterator) - bint operator<(reverse_iterator) - bint operator>(reverse_iterator) - bint operator<=(reverse_iterator) - bint operator>=(reverse_iterator) + bint operator==(reverse_iterator) + bint operator!=(reverse_iterator) + bint operator<(reverse_iterator) + bint operator>(reverse_iterator) + bint operator<=(reverse_iterator) + bint operator>=(reverse_iterator) cppclass const_iterator(iterator): pass @@ -50,34 +50,34 @@ cdef extern from "<util/generic/vector.h>" nogil: T& at(size_t) except + T& operator[](size_t) - T& back() - iterator begin() + T& back() + iterator begin() const_iterator const_begin "begin"() - size_t capacity() + size_t capacity() void clear() except + - bint empty() - iterator end() + bint empty() + iterator end() const_iterator const_end "end"() iterator erase(iterator) except + iterator erase(iterator, iterator) except + - T& front() + T& front() iterator insert(iterator, const T&) except + void insert(iterator, size_t, const T&) except + void insert[Iter](iterator, Iter, Iter) except + - size_t max_size() + size_t max_size() void pop_back() except + void push_back(T&) except + void emplace_back(...) except + - reverse_iterator rbegin() + reverse_iterator rbegin() const_reverse_iterator const_rbegin "rbegin"() - reverse_iterator rend() + reverse_iterator rend() const_reverse_iterator const_rend "rend"() void reserve(size_t) except + void resize(size_t) except + void resize(size_t, T&) except + - size_t size() + size_t size() void swap(TVector&) except + # C++11 methods - T* data() + T* data() void shrink_to_fit() except + diff --git a/util/generic/vector_ut.cpp b/util/generic/vector_ut.cpp index 24fb9a0544..0f6b4037a0 100644 --- a/util/generic/vector_ut.cpp +++ b/util/generic/vector_ut.cpp @@ -1,316 +1,316 @@ -#include "vector.h" +#include "vector.h" #include <library/cpp/testing/unittest/registar.h> - + #include <utility> -#include "yexception.h" +#include "yexception.h" + +#include <stdexcept> -#include <stdexcept> - class TYVectorTest: public TTestBase { - UNIT_TEST_SUITE(TYVectorTest); - UNIT_TEST(TestConstructorsAndAssignments) - UNIT_TEST(TestTildeEmptyToNull) - UNIT_TEST(TestTilde) - UNIT_TEST(Test1) - UNIT_TEST(Test2) - UNIT_TEST(Test3) - UNIT_TEST(Test4) - UNIT_TEST(Test5) - UNIT_TEST(Test6) - UNIT_TEST(Test7) - UNIT_TEST(TestCapacity) - UNIT_TEST(TestAt) - UNIT_TEST(TestPointer) - UNIT_TEST(TestAutoRef) - UNIT_TEST(TestIterators) - UNIT_TEST(TestShrink) - //UNIT_TEST(TestEbo) - UNIT_TEST(TestFillInConstructor) + UNIT_TEST_SUITE(TYVectorTest); + UNIT_TEST(TestConstructorsAndAssignments) + UNIT_TEST(TestTildeEmptyToNull) + UNIT_TEST(TestTilde) + UNIT_TEST(Test1) + UNIT_TEST(Test2) + UNIT_TEST(Test3) + UNIT_TEST(Test4) + UNIT_TEST(Test5) + UNIT_TEST(Test6) + UNIT_TEST(Test7) + UNIT_TEST(TestCapacity) + UNIT_TEST(TestAt) + UNIT_TEST(TestPointer) + UNIT_TEST(TestAutoRef) + UNIT_TEST(TestIterators) + UNIT_TEST(TestShrink) + //UNIT_TEST(TestEbo) + UNIT_TEST(TestFillInConstructor) UNIT_TEST(TestYResize) UNIT_TEST(TestCrop) UNIT_TEST(TestInitializeList) - UNIT_TEST_SUITE_END(); - -private: - void TestConstructorsAndAssignments() { + UNIT_TEST_SUITE_END(); + +private: + void TestConstructorsAndAssignments() { using container = TVector<int>; - container c1; - c1.push_back(100); - c1.push_back(200); + container c1; + c1.push_back(100); + c1.push_back(200); - container c2(c1); + container c2(c1); - UNIT_ASSERT_VALUES_EQUAL(2, c1.size()); - UNIT_ASSERT_VALUES_EQUAL(2, c2.size()); - UNIT_ASSERT_VALUES_EQUAL(100, c1.at(0)); - UNIT_ASSERT_VALUES_EQUAL(200, c2.at(1)); + UNIT_ASSERT_VALUES_EQUAL(2, c1.size()); + UNIT_ASSERT_VALUES_EQUAL(2, c2.size()); + UNIT_ASSERT_VALUES_EQUAL(100, c1.at(0)); + UNIT_ASSERT_VALUES_EQUAL(200, c2.at(1)); container c3(std::move(c1)); - UNIT_ASSERT_VALUES_EQUAL(0, c1.size()); - UNIT_ASSERT_VALUES_EQUAL(2, c3.size()); - UNIT_ASSERT_VALUES_EQUAL(100, c3.at(0)); + UNIT_ASSERT_VALUES_EQUAL(0, c1.size()); + UNIT_ASSERT_VALUES_EQUAL(2, c3.size()); + UNIT_ASSERT_VALUES_EQUAL(100, c3.at(0)); - c2.push_back(300); - c3 = c2; + c2.push_back(300); + c3 = c2; - UNIT_ASSERT_VALUES_EQUAL(3, c2.size()); - UNIT_ASSERT_VALUES_EQUAL(3, c3.size()); - UNIT_ASSERT_VALUES_EQUAL(300, c3.at(2)); + UNIT_ASSERT_VALUES_EQUAL(3, c2.size()); + UNIT_ASSERT_VALUES_EQUAL(3, c3.size()); + UNIT_ASSERT_VALUES_EQUAL(300, c3.at(2)); - c2.push_back(400); + c2.push_back(400); c3 = std::move(c2); - UNIT_ASSERT_VALUES_EQUAL(0, c2.size()); - UNIT_ASSERT_VALUES_EQUAL(4, c3.size()); - UNIT_ASSERT_VALUES_EQUAL(400, c3.at(3)); - } + UNIT_ASSERT_VALUES_EQUAL(0, c2.size()); + UNIT_ASSERT_VALUES_EQUAL(4, c3.size()); + UNIT_ASSERT_VALUES_EQUAL(400, c3.at(3)); + } - inline void TestTildeEmptyToNull() { + inline void TestTildeEmptyToNull() { TVector<int> v; UNIT_ASSERT_EQUAL(nullptr, v.data()); - } - - inline void TestTilde() { + } + + inline void TestTilde() { TVector<int> v; - v.push_back(10); - v.push_back(20); - + v.push_back(10); + v.push_back(20); + UNIT_ASSERT_EQUAL(10, (v.data())[0]); UNIT_ASSERT_EQUAL(20, (v.data())[1]); - - for (int i = 0; i < 10000; ++i) { - v.push_back(99); - } - + + for (int i = 0; i < 10000; ++i) { + v.push_back(99); + } + UNIT_ASSERT_EQUAL(10, (v.data())[0]); UNIT_ASSERT_EQUAL(20, (v.data())[1]); UNIT_ASSERT_EQUAL(99, (v.data())[3]); UNIT_ASSERT_EQUAL(99, (v.data())[4]); - } - - // Copy-paste of STLPort tests + } + + // Copy-paste of STLPort tests - void Test1() { + void Test1() { TVector<int> v1; // Empty vector of integers. - UNIT_ASSERT(v1.empty() == true); - UNIT_ASSERT(v1.size() == 0); - UNIT_ASSERT(!v1); + UNIT_ASSERT(v1.empty() == true); + UNIT_ASSERT(v1.size() == 0); + UNIT_ASSERT(!v1); - // UNIT_ASSERT(v1.max_size() == INT_MAX / sizeof(int)); - // cout << "max_size = " << v1.max_size() << endl; - v1.push_back(42); // Add an integer to the vector. + // UNIT_ASSERT(v1.max_size() == INT_MAX / sizeof(int)); + // cout << "max_size = " << v1.max_size() << endl; + v1.push_back(42); // Add an integer to the vector. - UNIT_ASSERT(v1.size() == 1); - UNIT_ASSERT(v1); + UNIT_ASSERT(v1.size() == 1); + UNIT_ASSERT(v1); - UNIT_ASSERT(v1[0] == 42); + UNIT_ASSERT(v1[0] == 42); - { + { TVector<TVector<int>> vect(10); TVector<TVector<int>>::iterator it(vect.begin()), end(vect.end()); - for (; it != end; ++it) { - UNIT_ASSERT((*it).empty()); - UNIT_ASSERT((*it).size() == 0); - UNIT_ASSERT((*it).capacity() == 0); - UNIT_ASSERT((*it).begin() == (*it).end()); + for (; it != end; ++it) { + UNIT_ASSERT((*it).empty()); + UNIT_ASSERT((*it).size() == 0); + UNIT_ASSERT((*it).capacity() == 0); + UNIT_ASSERT((*it).begin() == (*it).end()); } } - } + } - void Test2() { + void Test2() { TVector<double> v1; // Empty vector of doubles. - v1.push_back(32.1); - v1.push_back(40.5); + v1.push_back(32.1); + v1.push_back(40.5); TVector<double> v2; // Another empty vector of doubles. - v2.push_back(3.56); + v2.push_back(3.56); - UNIT_ASSERT(v1.size() == 2); - UNIT_ASSERT(v1[0] == 32.1); - UNIT_ASSERT(v1[1] == 40.5); + UNIT_ASSERT(v1.size() == 2); + UNIT_ASSERT(v1[0] == 32.1); + UNIT_ASSERT(v1[1] == 40.5); - UNIT_ASSERT(v2.size() == 1); - UNIT_ASSERT(v2[0] == 3.56); - v1.swap(v2); // Swap the vector's contents. + UNIT_ASSERT(v2.size() == 1); + UNIT_ASSERT(v2[0] == 3.56); + v1.swap(v2); // Swap the vector's contents. - UNIT_ASSERT(v1.size() == 1); - UNIT_ASSERT(v1[0] == 3.56); + UNIT_ASSERT(v1.size() == 1); + UNIT_ASSERT(v1[0] == 3.56); - UNIT_ASSERT(v2.size() == 2); - UNIT_ASSERT(v2[0] == 32.1); - UNIT_ASSERT(v2[1] == 40.5); + UNIT_ASSERT(v2.size() == 2); + UNIT_ASSERT(v2[0] == 32.1); + UNIT_ASSERT(v2[1] == 40.5); - v2 = v1; // Assign one vector to another. + v2 = v1; // Assign one vector to another. - UNIT_ASSERT(v2.size() == 1); - UNIT_ASSERT(v2[0] == 3.56); - } + UNIT_ASSERT(v2.size() == 1); + UNIT_ASSERT(v2[0] == 3.56); + } - void Test3() { + void Test3() { using vec_type = TVector<char>; - vec_type v1; // Empty vector of characters. - v1.push_back('h'); - v1.push_back('i'); + vec_type v1; // Empty vector of characters. + v1.push_back('h'); + v1.push_back('i'); - UNIT_ASSERT(v1.size() == 2); - UNIT_ASSERT(v1[0] == 'h'); - UNIT_ASSERT(v1[1] == 'i'); + UNIT_ASSERT(v1.size() == 2); + UNIT_ASSERT(v1[0] == 'h'); + UNIT_ASSERT(v1[1] == 'i'); - vec_type v2(v1.begin(), v1.end()); - v2[1] = 'o'; // Replace second character. + vec_type v2(v1.begin(), v1.end()); + v2[1] = 'o'; // Replace second character. - UNIT_ASSERT(v2.size() == 2); - UNIT_ASSERT(v2[0] == 'h'); - UNIT_ASSERT(v2[1] == 'o'); + UNIT_ASSERT(v2.size() == 2); + UNIT_ASSERT(v2[0] == 'h'); + UNIT_ASSERT(v2[1] == 'o'); - UNIT_ASSERT((v1 == v2) == false); + UNIT_ASSERT((v1 == v2) == false); - UNIT_ASSERT((v1 < v2) == true); - } + UNIT_ASSERT((v1 < v2) == true); + } - void Test4() { + void Test4() { TVector<int> v(4); - v[0] = 1; - v[1] = 4; - v[2] = 9; - v[3] = 16; + v[0] = 1; + v[1] = 4; + v[2] = 9; + v[3] = 16; - UNIT_ASSERT(v.front() == 1); - UNIT_ASSERT(v.back() == 16); + UNIT_ASSERT(v.front() == 1); + UNIT_ASSERT(v.back() == 16); - v.push_back(25); + v.push_back(25); - UNIT_ASSERT(v.back() == 25); - UNIT_ASSERT(v.size() == 5); + UNIT_ASSERT(v.back() == 25); + UNIT_ASSERT(v.size() == 5); - v.pop_back(); + v.pop_back(); - UNIT_ASSERT(v.back() == 16); - UNIT_ASSERT(v.size() == 4); - } + UNIT_ASSERT(v.back() == 16); + UNIT_ASSERT(v.size() == 4); + } - void Test5() { - int array[] = {1, 4, 9, 16}; + void Test5() { + int array[] = {1, 4, 9, 16}; TVector<int> v(array, array + 4); - UNIT_ASSERT(v.size() == 4); + UNIT_ASSERT(v.size() == 4); - UNIT_ASSERT(v[0] == 1); - UNIT_ASSERT(v[1] == 4); - UNIT_ASSERT(v[2] == 9); - UNIT_ASSERT(v[3] == 16); - } + UNIT_ASSERT(v[0] == 1); + UNIT_ASSERT(v[1] == 4); + UNIT_ASSERT(v[2] == 9); + UNIT_ASSERT(v[3] == 16); + } - void Test6() { - int array[] = {1, 4, 9, 16, 25, 36}; + void Test6() { + int array[] = {1, 4, 9, 16, 25, 36}; TVector<int> v(array, array + 6); TVector<int>::iterator vit; - UNIT_ASSERT(v.size() == 6); - UNIT_ASSERT(v[0] == 1); - UNIT_ASSERT(v[1] == 4); - UNIT_ASSERT(v[2] == 9); - UNIT_ASSERT(v[3] == 16); - UNIT_ASSERT(v[4] == 25); - UNIT_ASSERT(v[5] == 36); - - vit = v.erase(v.begin()); // Erase first element. - UNIT_ASSERT(*vit == 4); - - UNIT_ASSERT(v.size() == 5); - UNIT_ASSERT(v[0] == 4); - UNIT_ASSERT(v[1] == 9); - UNIT_ASSERT(v[2] == 16); - UNIT_ASSERT(v[3] == 25); - UNIT_ASSERT(v[4] == 36); - - vit = v.erase(v.end() - 1); // Erase last element. - UNIT_ASSERT(vit == v.end()); - - UNIT_ASSERT(v.size() == 4); - UNIT_ASSERT(v[0] == 4); - UNIT_ASSERT(v[1] == 9); - UNIT_ASSERT(v[2] == 16); - UNIT_ASSERT(v[3] == 25); - - v.erase(v.begin() + 1, v.end() - 1); // Erase all but first and last. - - UNIT_ASSERT(v.size() == 2); - UNIT_ASSERT(v[0] == 4); - UNIT_ASSERT(v[1] == 25); - } + UNIT_ASSERT(v.size() == 6); + UNIT_ASSERT(v[0] == 1); + UNIT_ASSERT(v[1] == 4); + UNIT_ASSERT(v[2] == 9); + UNIT_ASSERT(v[3] == 16); + UNIT_ASSERT(v[4] == 25); + UNIT_ASSERT(v[5] == 36); + + vit = v.erase(v.begin()); // Erase first element. + UNIT_ASSERT(*vit == 4); + + UNIT_ASSERT(v.size() == 5); + UNIT_ASSERT(v[0] == 4); + UNIT_ASSERT(v[1] == 9); + UNIT_ASSERT(v[2] == 16); + UNIT_ASSERT(v[3] == 25); + UNIT_ASSERT(v[4] == 36); + + vit = v.erase(v.end() - 1); // Erase last element. + UNIT_ASSERT(vit == v.end()); + + UNIT_ASSERT(v.size() == 4); + UNIT_ASSERT(v[0] == 4); + UNIT_ASSERT(v[1] == 9); + UNIT_ASSERT(v[2] == 16); + UNIT_ASSERT(v[3] == 25); + + v.erase(v.begin() + 1, v.end() - 1); // Erase all but first and last. + + UNIT_ASSERT(v.size() == 2); + UNIT_ASSERT(v[0] == 4); + UNIT_ASSERT(v[1] == 25); + } - void Test7() { - int array1[] = {1, 4, 25}; - int array2[] = {9, 16}; + void Test7() { + int array1[] = {1, 4, 25}; + int array2[] = {9, 16}; TVector<int> v(array1, array1 + 3); TVector<int>::iterator vit; - vit = v.insert(v.begin(), 0); // Insert before first element. - UNIT_ASSERT(*vit == 0); + vit = v.insert(v.begin(), 0); // Insert before first element. + UNIT_ASSERT(*vit == 0); - vit = v.insert(v.end(), 36); // Insert after last element. - UNIT_ASSERT(*vit == 36); + vit = v.insert(v.end(), 36); // Insert after last element. + UNIT_ASSERT(*vit == 36); - UNIT_ASSERT(v.size() == 5); - UNIT_ASSERT(v[0] == 0); - UNIT_ASSERT(v[1] == 1); - UNIT_ASSERT(v[2] == 4); - UNIT_ASSERT(v[3] == 25); - UNIT_ASSERT(v[4] == 36); + UNIT_ASSERT(v.size() == 5); + UNIT_ASSERT(v[0] == 0); + UNIT_ASSERT(v[1] == 1); + UNIT_ASSERT(v[2] == 4); + UNIT_ASSERT(v[3] == 25); + UNIT_ASSERT(v[4] == 36); - // Insert contents of array2 before fourth element. - v.insert(v.begin() + 3, array2, array2 + 2); + // Insert contents of array2 before fourth element. + v.insert(v.begin() + 3, array2, array2 + 2); - UNIT_ASSERT(v.size() == 7); + UNIT_ASSERT(v.size() == 7); - UNIT_ASSERT(v[0] == 0); - UNIT_ASSERT(v[1] == 1); - UNIT_ASSERT(v[2] == 4); - UNIT_ASSERT(v[3] == 9); - UNIT_ASSERT(v[4] == 16); - UNIT_ASSERT(v[5] == 25); - UNIT_ASSERT(v[6] == 36); + UNIT_ASSERT(v[0] == 0); + UNIT_ASSERT(v[1] == 1); + UNIT_ASSERT(v[2] == 4); + UNIT_ASSERT(v[3] == 9); + UNIT_ASSERT(v[4] == 16); + UNIT_ASSERT(v[5] == 25); + UNIT_ASSERT(v[6] == 36); size_t curCapacity = v.capacity(); - v.clear(); - UNIT_ASSERT(v.empty()); + v.clear(); + UNIT_ASSERT(v.empty()); //check that clear save reserved data UNIT_ASSERT_EQUAL(curCapacity, v.capacity()); - v.insert(v.begin(), 5, 10); - UNIT_ASSERT(v.size() == 5); - UNIT_ASSERT(v[0] == 10); - UNIT_ASSERT(v[1] == 10); - UNIT_ASSERT(v[2] == 10); - UNIT_ASSERT(v[3] == 10); - UNIT_ASSERT(v[4] == 10); - } - - struct TestStruct { - unsigned int a[3]; - }; - - void TestCapacity() { - { + v.insert(v.begin(), 5, 10); + UNIT_ASSERT(v.size() == 5); + UNIT_ASSERT(v[0] == 10); + UNIT_ASSERT(v[1] == 10); + UNIT_ASSERT(v[2] == 10); + UNIT_ASSERT(v[3] == 10); + UNIT_ASSERT(v[4] == 10); + } + + struct TestStruct { + unsigned int a[3]; + }; + + void TestCapacity() { + { TVector<int> v; - UNIT_ASSERT(v.capacity() == 0); - v.push_back(42); - UNIT_ASSERT(v.capacity() >= 1); - v.reserve(5000); - UNIT_ASSERT(v.capacity() >= 5000); - } + UNIT_ASSERT(v.capacity() == 0); + v.push_back(42); + UNIT_ASSERT(v.capacity() >= 1); + v.reserve(5000); + UNIT_ASSERT(v.capacity() >= 5000); + } - { + { TVector<int> v(Reserve(100)); UNIT_ASSERT(v.capacity() >= 100); @@ -318,158 +318,158 @@ private: } { - //Test that used to generate an assertion when using __debug_alloc. + //Test that used to generate an assertion when using __debug_alloc. TVector<TestStruct> va; - va.reserve(1); - va.reserve(2); + va.reserve(1); + va.reserve(2); } - } + } - void TestAt() { + void TestAt() { TVector<int> v; TVector<int> const& cv = v; - v.push_back(10); - UNIT_ASSERT(v.at(0) == 10); - v.at(0) = 20; - UNIT_ASSERT(cv.at(0) == 20); - - for (;;) { - try { - v.at(1) = 20; - UNIT_ASSERT(false); - } catch (std::out_of_range const&) { - return; - } catch (...) { - UNIT_ASSERT(false); + v.push_back(10); + UNIT_ASSERT(v.at(0) == 10); + v.at(0) = 20; + UNIT_ASSERT(cv.at(0) == 20); + + for (;;) { + try { + v.at(1) = 20; + UNIT_ASSERT(false); + } catch (std::out_of_range const&) { + return; + } catch (...) { + UNIT_ASSERT(false); } } - } + } - void TestPointer() { + void TestPointer() { TVector<int*> v1; TVector<int*> v2 = v1; TVector<int*> v3; - v3.insert(v3.end(), v1.begin(), v1.end()); - } - - void TestAutoRef() { + v3.insert(v3.end(), v1.begin(), v1.end()); + } + + void TestAutoRef() { TVector<int> ref; - for (int i = 0; i < 5; ++i) { - ref.push_back(i); + for (int i = 0; i < 5; ++i) { + ref.push_back(i); } TVector<TVector<int>> v_v_int(1, ref); - v_v_int.push_back(v_v_int[0]); - v_v_int.push_back(ref); - v_v_int.push_back(v_v_int[0]); - v_v_int.push_back(v_v_int[0]); - v_v_int.push_back(ref); + v_v_int.push_back(v_v_int[0]); + v_v_int.push_back(ref); + v_v_int.push_back(v_v_int[0]); + v_v_int.push_back(v_v_int[0]); + v_v_int.push_back(ref); TVector<TVector<int>>::iterator vvit(v_v_int.begin()), vvitEnd(v_v_int.end()); - for (; vvit != vvitEnd; ++vvit) { - UNIT_ASSERT(*vvit == ref); + for (; vvit != vvitEnd; ++vvit) { + UNIT_ASSERT(*vvit == ref); + } + } + + struct Point { + int x, y; + }; + + struct PointEx: public Point { + PointEx() + : builtFromBase(false) + { } - } - - struct Point { - int x, y; - }; - - struct PointEx: public Point { - PointEx() - : builtFromBase(false) - { - } - PointEx(const Point&) - : builtFromBase(true) - { - } - - bool builtFromBase; - }; - - void TestIterators() { + PointEx(const Point&) + : builtFromBase(true) + { + } + + bool builtFromBase; + }; + + void TestIterators() { TVector<int> vint(10, 0); TVector<int> const& crvint = vint; - UNIT_ASSERT(vint.begin() == vint.begin()); - UNIT_ASSERT(crvint.begin() == vint.begin()); - UNIT_ASSERT(vint.begin() == crvint.begin()); - UNIT_ASSERT(crvint.begin() == crvint.begin()); - - UNIT_ASSERT(vint.begin() != vint.end()); - UNIT_ASSERT(crvint.begin() != vint.end()); - UNIT_ASSERT(vint.begin() != crvint.end()); - UNIT_ASSERT(crvint.begin() != crvint.end()); - - UNIT_ASSERT(vint.rbegin() == vint.rbegin()); - // Not Standard: - //UNIT_ASSERT(vint.rbegin() == crvint.rbegin()); - //UNIT_ASSERT(crvint.rbegin() == vint.rbegin()); - UNIT_ASSERT(crvint.rbegin() == crvint.rbegin()); - - UNIT_ASSERT(vint.rbegin() != vint.rend()); - // Not Standard: - //UNIT_ASSERT(vint.rbegin() != crvint.rend()); - //UNIT_ASSERT(crvint.rbegin() != vint.rend()); - UNIT_ASSERT(crvint.rbegin() != crvint.rend()); - } - - void TestShrink() { + UNIT_ASSERT(vint.begin() == vint.begin()); + UNIT_ASSERT(crvint.begin() == vint.begin()); + UNIT_ASSERT(vint.begin() == crvint.begin()); + UNIT_ASSERT(crvint.begin() == crvint.begin()); + + UNIT_ASSERT(vint.begin() != vint.end()); + UNIT_ASSERT(crvint.begin() != vint.end()); + UNIT_ASSERT(vint.begin() != crvint.end()); + UNIT_ASSERT(crvint.begin() != crvint.end()); + + UNIT_ASSERT(vint.rbegin() == vint.rbegin()); + // Not Standard: + //UNIT_ASSERT(vint.rbegin() == crvint.rbegin()); + //UNIT_ASSERT(crvint.rbegin() == vint.rbegin()); + UNIT_ASSERT(crvint.rbegin() == crvint.rbegin()); + + UNIT_ASSERT(vint.rbegin() != vint.rend()); + // Not Standard: + //UNIT_ASSERT(vint.rbegin() != crvint.rend()); + //UNIT_ASSERT(crvint.rbegin() != vint.rend()); + UNIT_ASSERT(crvint.rbegin() != crvint.rend()); + } + + void TestShrink() { TVector<int> v; - v.resize(1000); - v.resize(10); - v.shrink_to_fit(); - UNIT_ASSERT_EQUAL(v.capacity(), 10); - v.push_back(0); - v.shrink_to_fit(); - UNIT_ASSERT_EQUAL(v.capacity(), 11); - } - - /* This test check a potential issue with empty base class + v.resize(1000); + v.resize(10); + v.shrink_to_fit(); + UNIT_ASSERT_EQUAL(v.capacity(), 10); + v.push_back(0); + v.shrink_to_fit(); + UNIT_ASSERT_EQUAL(v.capacity(), 11); + } + + /* This test check a potential issue with empty base class * optimization. Some compilers (VC6) do not implement it * correctly resulting ina wrong behavior. */ - void TestEbo() { - // We use heap memory as test failure can corrupt vector internal - // representation making executable crash on vector destructor invocation. - // We prefer a simple memory leak, internal corruption should be reveal - // by size or capacity checks. + void TestEbo() { + // We use heap memory as test failure can corrupt vector internal + // representation making executable crash on vector destructor invocation. + // We prefer a simple memory leak, internal corruption should be reveal + // by size or capacity checks. using V = TVector<int>; - V* pv1 = new V(1, 1); - V* pv2 = new V(10, 2); + V* pv1 = new V(1, 1); + V* pv2 = new V(10, 2); - size_t v1Capacity = pv1->capacity(); - size_t v2Capacity = pv2->capacity(); + size_t v1Capacity = pv1->capacity(); + size_t v2Capacity = pv2->capacity(); - pv1->swap(*pv2); + pv1->swap(*pv2); - UNIT_ASSERT(pv1->size() == 10); - UNIT_ASSERT(pv1->capacity() == v2Capacity); - UNIT_ASSERT((*pv1)[5] == 2); + UNIT_ASSERT(pv1->size() == 10); + UNIT_ASSERT(pv1->capacity() == v2Capacity); + UNIT_ASSERT((*pv1)[5] == 2); - UNIT_ASSERT(pv2->size() == 1); - UNIT_ASSERT(pv2->capacity() == v1Capacity); - UNIT_ASSERT((*pv2)[0] == 1); + UNIT_ASSERT(pv2->size() == 1); + UNIT_ASSERT(pv2->capacity() == v1Capacity); + UNIT_ASSERT((*pv2)[0] == 1); - delete pv2; - delete pv1; - } + delete pv2; + delete pv1; + } - void TestFillInConstructor() { - for (int k = 0; k < 3; ++k) { + void TestFillInConstructor() { + for (int k = 0; k < 3; ++k) { TVector<int> v(100); - UNIT_ASSERT_VALUES_EQUAL(100u, v.size()); - for (size_t i = 0; i < v.size(); ++i) { - UNIT_ASSERT_VALUES_EQUAL(0, v[i]); + UNIT_ASSERT_VALUES_EQUAL(100u, v.size()); + for (size_t i = 0; i < v.size(); ++i) { + UNIT_ASSERT_VALUES_EQUAL(0, v[i]); + } + // fill with garbage for the next iteration + for (size_t i = 0; i < v.size(); ++i) { + v[i] = 10; } - // fill with garbage for the next iteration - for (size_t i = 0; i < v.size(); ++i) { - v[i] = 10; - } } - } + } struct TPod { int x; @@ -490,8 +490,8 @@ private: } }; - template <typename T> - class TDebugAlloc: public std::allocator<T> { + template <typename T> + class TDebugAlloc: public std::allocator<T> { public: using TBase = std::allocator<T>; @@ -503,13 +503,13 @@ private: return p; } - template <class TOther> + template <class TOther> struct rebind { using other = TDebugAlloc<TOther>; }; }; - template <typename T> + template <typename T> void TestYResize() { #ifdef _YNDX_LIBCXX_ENABLE_VECTOR_POD_RESIZE_UNINITIALIZED constexpr bool ALLOW_UNINITIALIZED = std::is_pod_v<T>; @@ -537,10 +537,10 @@ private: struct TNoDefaultConstructor { TNoDefaultConstructor() = delete; - explicit TNoDefaultConstructor(int val) - : Val(val) - { - } + explicit TNoDefaultConstructor(int val) + : Val(val) + { + } int Val; }; diff --git a/util/generic/xrange.h b/util/generic/xrange.h index e21398f7f9..5fc8c82912 100644 --- a/util/generic/xrange.h +++ b/util/generic/xrange.h @@ -1,9 +1,9 @@ #pragma once -#include "typetraits.h" +#include "typetraits.h" #include "utility.h" #include <util/system/yassert.h> -#include <iterator> +#include <iterator> /** @file * Some similar for python xrange(): https://docs.python.org/2/library/functions.html#xrange @@ -25,9 +25,9 @@ namespace NPrivate { public: constexpr TSimpleXRange(T start, T finish) noexcept - : Start(start) - , Finish(Max(start, finish)) - { + : Start(start) + , Finish(Max(start, finish)) + { } class TIterator { @@ -59,7 +59,7 @@ namespace NPrivate { ++Value; return *this; } - + TIterator& operator--() noexcept { --Value; return *this; @@ -69,18 +69,18 @@ namespace NPrivate { return Value - b.Value; } - template <typename IntType> + template <typename IntType> constexpr TIterator operator+(const IntType& b) const noexcept { return TIterator(Value + b); } - template <typename IntType> + template <typename IntType> TIterator& operator+=(const IntType& b) noexcept { Value += b; return *this; } - template <typename IntType> + template <typename IntType> constexpr TIterator operator-(const IntType& b) const noexcept { return TIterator(Value - b); } @@ -110,13 +110,13 @@ namespace NPrivate { constexpr TIterator end() const noexcept { return TIterator(Finish); } - + constexpr T size() const noexcept { return Finish - Start; } template <class Container> - operator Container() const { + operator Container() const { return Container(begin(), end()); } @@ -128,13 +128,13 @@ namespace NPrivate { template <typename T> class TSteppedXRange { using TDiff = decltype(T() - T()); - + public: constexpr TSteppedXRange(T start, T finish, TDiff step) noexcept - : Start_(start) - , Step_(step) - , Finish_(CalcRealFinish(Start_, finish, Step_)) - { + : Start_(start) + , Step_(step) + , Finish_(CalcRealFinish(Start_, finish, Step_)) + { static_assert(std::is_integral<T>::value || std::is_pointer<T>::value, "T should be integral type or pointer"); } @@ -147,9 +147,9 @@ namespace NPrivate { using iterator_category = std::random_access_iterator_tag; constexpr TIterator(T value, const TSteppedXRange& parent) noexcept - : Value_(value) + : Value_(value) , Parent_(&parent) - { + { } constexpr T operator*() const noexcept { @@ -178,22 +178,22 @@ namespace NPrivate { return (Value_ - b.Value_) / Parent_->Step_; } - template <typename IntType> + template <typename IntType> constexpr TIterator operator+(const IntType& b) const noexcept { return TIterator(*this) += b; } - template <typename IntType> + template <typename IntType> TIterator& operator+=(const IntType& b) noexcept { Value_ += b * Parent_->Step_; return *this; } - template <typename IntType> + template <typename IntType> constexpr TIterator operator-(const IntType& b) const noexcept { return TIterator(*this) -= b; } - + template <typename IntType> TIterator& operator-=(const IntType& b) noexcept { Value_ -= b * Parent_->Step_; @@ -233,7 +233,7 @@ namespace NPrivate { } template <class Container> - operator Container() const { + operator Container() const { return Container(begin(), end()); } @@ -243,7 +243,7 @@ namespace NPrivate { const T Finish_; }; -} +} /** * generate arithmetic progression that starts at start with certain step and stop at finish (not including) @@ -252,13 +252,13 @@ namespace NPrivate { */ template <typename T> constexpr ::NPrivate::TSteppedXRange<T> xrange(T start, T finish, decltype(T() - T()) step) noexcept { - return {start, finish, step}; + return {start, finish, step}; } /// generate sequence [start; finish) template <typename T> constexpr ::NPrivate::TSimpleXRange<T> xrange(T start, T finish) noexcept { - return {start, finish}; + return {start, finish}; } /// generate sequence [0; finish) diff --git a/util/generic/xrange_ut.cpp b/util/generic/xrange_ut.cpp index 35fba4ea10..8106da03e7 100644 --- a/util/generic/xrange_ut.cpp +++ b/util/generic/xrange_ut.cpp @@ -1,8 +1,8 @@ #include "xrange.h" -#include "algorithm.h" +#include "algorithm.h" #include "maybe.h" -#include "vector.h" +#include "vector.h" #include <library/cpp/testing/unittest/registar.h> #include <util/string/builder.h> @@ -14,7 +14,7 @@ Y_UNIT_TEST_SUITE(XRange) { bool firstInited = false; size_t last = 0; - for (auto i : xrange(begin, end)) { + for (auto i : xrange(begin, end)) { ++count; sum += i; last = i; @@ -32,7 +32,7 @@ Y_UNIT_TEST_SUITE(XRange) { void TestSteppedXRangeImpl(int begin, int end, int step, const TVector<int>& expected) { size_t expInd = 0; - for (auto i : xrange(begin, end, step)) { + for (auto i : xrange(begin, end, step)) { UNIT_ASSERT(expInd < expected.size()); UNIT_ASSERT_VALUES_EQUAL(i, expected[expInd]); ++expInd; @@ -68,12 +68,12 @@ Y_UNIT_TEST_SUITE(XRange) { TVector<size_t> data = {3, 1, 4, 1, 5, 9, 2, 6}; const size_t digSumExpected = Accumulate(data.begin(), data.end(), static_cast<size_t>(0)); size_t digSumByIt = 0; - for (auto ptr : xrange(data.begin(), data.end())) { + for (auto ptr : xrange(data.begin(), data.end())) { digSumByIt += *ptr; } UNIT_ASSERT_VALUES_EQUAL(digSumByIt, digSumExpected); size_t digSumByPtr = 0; - for (auto ptr : xrange(&data[0], &data[0] + data.size())) { + for (auto ptr : xrange(&data[0], &data[0] + data.size())) { digSumByPtr += *ptr; } UNIT_ASSERT_VALUES_EQUAL(digSumByPtr, digSumExpected); @@ -87,26 +87,26 @@ Y_UNIT_TEST_SUITE(XRange) { class TVectorChild: public TVector<size_t> { public: - template <typename TIterator> - TVectorChild(TIterator a, TIterator b) + template <typename TIterator> + TVectorChild(TIterator a, TIterator b) : TVector<size_t>(a, b) - { - } + { + } }; Y_UNIT_TEST(ConvertionWorks) { TVector<size_t> data = {0, 1, 2, 3, 4, 5, 6, 7, 8}; TVector<size_t> convertionResults[] = {xrange<size_t>(9), - xrange<ui32>(0, 9), - xrange(0, 9, 1)}; + xrange<ui32>(0, 9), + xrange(0, 9, 1)}; for (const auto& arr : convertionResults) { UNIT_ASSERT(arr == data); } TVectorChild sons[] = {xrange(0, 9), - xrange(0, 9, 1)}; + xrange(0, 9, 1)}; for (const auto& arr : sons) { UNIT_ASSERT(arr == data); @@ -150,7 +150,7 @@ Y_UNIT_TEST_SUITE(XRange) { xrange(5, 5, 1), xrange(5, 0, 5), xrange(0, -1, 5), - xrange(0, 1, -1), + xrange(0, 1, -1), xrange(0, -10, 10), }; diff --git a/util/generic/yexception.cpp b/util/generic/yexception.cpp index a8ef36bd50..2ce6c4369d 100644 --- a/util/generic/yexception.cpp +++ b/util/generic/yexception.cpp @@ -1,19 +1,19 @@ #include "bt_exception.h" #include "yexception.h" - -#include <util/system/backtrace.h> + +#include <util/system/backtrace.h> #include <util/system/type_name.h> - + #include <cxxabi.h> -#include <stdexcept> - -#include <cstdio> - -TString FormatExc(const std::exception& exception) { +#include <stdexcept> + +#include <cstdio> + +TString FormatExc(const std::exception& exception) { return TString::Join(TStringBuf("("), TypeName(exception), TStringBuf(") "), exception.what()); -} - +} + TString CurrentExceptionMessage() { auto exceptionPtr = std::current_exception(); if (exceptionPtr) { @@ -21,7 +21,7 @@ TString CurrentExceptionMessage() { std::rethrow_exception(exceptionPtr); } catch (const yexception& e) { const TBackTrace* bt = e.BackTrace(); - + if (bt) { return TString::Join(bt->PrintToString(), TStringBuf("\n"), FormatExc(e)); } @@ -30,23 +30,23 @@ TString CurrentExceptionMessage() { } catch (const std::exception& e) { return FormatExc(e); } catch (...) { - } - + } + return "unknown error"; - } - + } + return "(NO EXCEPTION)"; -} - +} + bool UncaughtException() noexcept { // FIXME: use std::uncaught_exceptions() unconditionally after DEVTOOLS-8811 #if defined(__cpp_lib_uncaught_exceptions) && !defined(_LIBCPP_AVAILABILITY_UNCAUGHT_EXCEPTIONS) return std::uncaught_exceptions() > 0; #else - return std::uncaught_exception(); + return std::uncaught_exception(); #endif -} - +} + std::string CurrentExceptionTypeName() { #if defined(_linux_) || defined(_darwin_) std::type_info* currentExceptionTypePtr = abi::__cxa_current_exception_type(); @@ -67,18 +67,18 @@ std::string CurrentExceptionTypeName() { } } -void TSystemError::Init() { - yexception& exc = *this; - +void TSystemError::Init() { + yexception& exc = *this; + exc << TStringBuf("("); exc << TStringBuf(LastSystemErrorText(Status_)); exc << TStringBuf(") "); -} - +} + NPrivateException::yexception::yexception() { ZeroTerminate(); } - + TStringBuf NPrivateException::yexception::AsStrBuf() const { if (Buf_.Left()) { return TStringBuf(Buf_.Data(), Buf_.Filled()); @@ -91,27 +91,27 @@ void NPrivateException::yexception::ZeroTerminate() noexcept { char* end = (char*)Buf_.Current(); if (!Buf_.Left()) { - --end; - } - - *end = 0; -} - + --end; + } + + *end = 0; +} + const char* NPrivateException::yexception::what() const noexcept { return Buf_.Data(); -} - +} + const TBackTrace* NPrivateException::yexception::BackTrace() const noexcept { return nullptr; -} - -void fputs(const std::exception& e, FILE* f) { - char message[256]; - size_t len = Min(sizeof(message) - 2, strlcpy(message, e.what(), sizeof(message) - 1)); - message[len++] = '\n'; - message[len] = 0; - fputs(message, f); -} +} + +void fputs(const std::exception& e, FILE* f) { + char message[256]; + size_t len = Min(sizeof(message) - 2, strlcpy(message, e.what(), sizeof(message) - 1)); + message[len++] = '\n'; + message[len] = 0; + fputs(message, f); +} void ::NPrivate::ThrowYException(const ::NPrivate::TSimpleExceptionMessage& sm) { throw sm.Location + yexception() << sm.Message; diff --git a/util/generic/yexception.h b/util/generic/yexception.h index 33eebd9462..b0c604e8c4 100644 --- a/util/generic/yexception.h +++ b/util/generic/yexception.h @@ -3,25 +3,25 @@ #include "bt_exception.h" #include "strbuf.h" #include "string.h" -#include "utility.h" +#include "utility.h" #include "va_args.h" #include <utility> - + #include <util/stream/tempbuf.h> #include <util/system/compat.h> #include <util/system/compiler.h> #include <util/system/defaults.h> -#include <util/system/error.h> -#include <util/system/src_location.h> +#include <util/system/error.h> +#include <util/system/src_location.h> #include <util/system/platform.h> - -#include <exception> - -#include <cstdio> - -class TBackTrace; - -namespace NPrivateException { + +#include <exception> + +#include <cstdio> + +class TBackTrace; + +namespace NPrivateException { class TTempBufCuttingWrapperOutput: public IOutputStream { public: TTempBufCuttingWrapperOutput(TTempBuf& tempbuf) @@ -37,8 +37,8 @@ namespace NPrivateException { TTempBuf& TempBuf_; }; - class yexception: public std::exception { - public: + class yexception: public std::exception { + public: yexception(); yexception(const yexception&) = default; yexception(yexception&&) = default; @@ -49,76 +49,76 @@ namespace NPrivateException { const char* what() const noexcept override; virtual const TBackTrace* BackTrace() const noexcept; - template <class T> - inline void Append(const T& t) { + template <class T> + inline void Append(const T& t) { TTempBufCuttingWrapperOutput tempBuf(Buf_); static_cast<IOutputStream&>(tempBuf) << t; ZeroTerminate(); - } - + } + TStringBuf AsStrBuf() const; - private: + private: void ZeroTerminate() noexcept; private: TTempBuf Buf_; - }; - - template <class E, class T> + }; + + template <class E, class T> static inline std::enable_if_t<std::is_base_of<yexception, std::decay_t<E>>::value, E&&> operator<<(E&& e, const T& t) { - e.Append(t); - + e.Append(t); + return std::forward<E>(e); - } - - template <class T> - static inline T&& operator+(const TSourceLocation& sl, T&& t) { + } + + template <class T> + static inline T&& operator+(const TSourceLocation& sl, T&& t) { return std::forward<T>(t << sl << TStringBuf(": ")); - } -} - -class yexception: public NPrivateException::yexception { -}; - + } +} + +class yexception: public NPrivateException::yexception { +}; + Y_DECLARE_OUT_SPEC(inline, yexception, stream, value) { stream << value.AsStrBuf(); } class TSystemError: public yexception { -public: +public: TSystemError(int status) : Status_(status) - { - Init(); - } - + { + Init(); + } + TSystemError() : TSystemError(LastSystemError()) - { - } + { + } int Status() const noexcept { return Status_; - } - -private: - void Init(); + } + +private: + void Init(); private: int Status_; -}; - +}; + class TIoException: public TSystemError { -}; - +}; + class TIoSystemError: public TIoException { -}; - -class TFileError: public TIoSystemError { -}; - +}; + +class TFileError: public TIoSystemError { +}; + /** * TBadArgumentException should be thrown when an argument supplied to some function (or constructor) * is invalid or incorrect. @@ -138,8 +138,8 @@ struct TBadArgumentException: public virtual yexception { struct TBadCastException: public virtual TBadArgumentException { }; -#define ythrow throw __LOCATION__ + - +#define ythrow throw __LOCATION__ + + namespace NPrivate { /// Encapsulates data for one of the most common case in which /// exception message contists of single constant string @@ -152,7 +152,7 @@ namespace NPrivate { [[noreturn]] void ThrowYExceptionWithBacktrace(const TSimpleExceptionMessage& sm); } -void fputs(const std::exception& e, FILE* f = stderr); +void fputs(const std::exception& e, FILE* f = stderr); TString CurrentExceptionMessage(); @@ -172,7 +172,7 @@ TString CurrentExceptionMessage(); bool UncaughtException() noexcept; std::string CurrentExceptionTypeName(); - + TString FormatExc(const std::exception& exception); #define Y_ENSURE_EX(CONDITION, THROW_EXPRESSION) \ diff --git a/util/generic/yexception_ut.cpp b/util/generic/yexception_ut.cpp index 9e643acf0c..cb3e29fed8 100644 --- a/util/generic/yexception_ut.cpp +++ b/util/generic/yexception_ut.cpp @@ -1,26 +1,26 @@ -#include "yexception.h" - -static inline void Throw1DontMove() { +#include "yexception.h" + +static inline void Throw1DontMove() { ythrow yexception() << "blabla"; // don't move this line -} - -static inline void Throw2DontMove() { +} + +static inline void Throw2DontMove() { ythrow yexception() << 1 << " qw " << 12.1; // don't move this line -} - +} + #include <library/cpp/testing/unittest/registar.h> - + #include <util/generic/algorithm.h> #include <util/memory/tempbuf.h> #include <util/random/mersenne.h> #include <util/stream/output.h> #include <util/string/subst.h> - + #include "yexception_ut.h" -#include "bt_exception.h" +#include "bt_exception.h" -#if defined(_MSC_VER) - #pragma warning(disable : 4702) /*unreachable code*/ +#if defined(_MSC_VER) + #pragma warning(disable : 4702) /*unreachable code*/ #endif static void CallbackFun(int i) { @@ -28,64 +28,64 @@ static void CallbackFun(int i) { } static IOutputStream* OUTS = nullptr; - + namespace NOuter::NInner { void Compare10And20() { Y_ENSURE(10 > 20); } } -class TExceptionTest: public TTestBase { - UNIT_TEST_SUITE(TExceptionTest); - UNIT_TEST_EXCEPTION(TestException, yexception) - UNIT_TEST_EXCEPTION(TestLineInfo, yexception) +class TExceptionTest: public TTestBase { + UNIT_TEST_SUITE(TExceptionTest); + UNIT_TEST_EXCEPTION(TestException, yexception) + UNIT_TEST_EXCEPTION(TestLineInfo, yexception) UNIT_TEST(TestCurrentExceptionMessageWhenThereisNoException) - UNIT_TEST(TestFormat1) - UNIT_TEST(TestRaise1) - UNIT_TEST(TestVirtuality) - UNIT_TEST(TestVirtualInheritance) - UNIT_TEST(TestMixedCode) - UNIT_TEST(TestBackTrace) + UNIT_TEST(TestFormat1) + UNIT_TEST(TestRaise1) + UNIT_TEST(TestVirtuality) + UNIT_TEST(TestVirtualInheritance) + UNIT_TEST(TestMixedCode) + UNIT_TEST(TestBackTrace) UNIT_TEST(TestEnsureWithBackTrace1) UNIT_TEST(TestEnsureWithBackTrace2) - UNIT_TEST(TestRethrowAppend) + UNIT_TEST(TestRethrowAppend) UNIT_TEST(TestMacroOverload) UNIT_TEST(TestMessageCrop) UNIT_TEST(TestTIoSystemErrorSpecialMethods) UNIT_TEST(TestCurrentExceptionTypeNameMethod) - UNIT_TEST_SUITE_END(); - -private: - inline void TestRethrowAppend() { - try { - try { + UNIT_TEST_SUITE_END(); + +private: + inline void TestRethrowAppend() { + try { + try { ythrow yexception() << "it"; - } catch (yexception& e) { - e << "happens"; - - throw; - } - } catch (...) { + } catch (yexception& e) { + e << "happens"; + + throw; + } + } catch (...) { UNIT_ASSERT(CurrentExceptionMessage().Contains("ithappens")); - } - } - + } + } + inline void TestCurrentExceptionMessageWhenThereisNoException() { UNIT_ASSERT(CurrentExceptionMessage() == "(NO EXCEPTION)"); } - inline void TestBackTrace() { - try { - ythrow TWithBackTrace<TIoSystemError>() << "test"; - } catch (...) { + inline void TestBackTrace() { + try { + ythrow TWithBackTrace<TIoSystemError>() << "test"; + } catch (...) { UNIT_ASSERT(CurrentExceptionMessage().find('\n') != TString::npos); - - return; - } - - UNIT_ASSERT(false); - } - + + return; + } + + UNIT_ASSERT(false); + } + template <typename TException> static void EnsureCurrentExceptionHasBackTrace() { auto exceptionPtr = std::current_exception(); @@ -115,8 +115,8 @@ private: inline void TestEnsureWithBackTrace2() { try { - Y_ENSURE_BT(4 > 6, "custom " - << "message"); + Y_ENSURE_BT(4 > 6, "custom " + << "message"); } catch (...) { const TString msg = CurrentExceptionMessage(); UNIT_ASSERT(!msg.Contains("4 > 6")); @@ -128,138 +128,138 @@ private: UNIT_ASSERT(false); } - inline void TestVirtualInheritance() { - TStringStream ss; - - OUTS = &ss; - - class TA { - public: - inline TA() { - *OUTS << "A"; - } - }; - - class TB { - public: - inline TB() { - *OUTS << "B"; - } - }; - - class TC: public virtual TB, public virtual TA { - public: - inline TC() { - *OUTS << "C"; - } - }; - - class TD: public virtual TA { - public: - inline TD() { - *OUTS << "D"; - } - }; - - class TE: public TC, public TD { - public: - inline TE() { - *OUTS << "E"; - } - }; - - TE e; - - UNIT_ASSERT_EQUAL(ss.Str(), "BACDE"); - } - - inline void TestVirtuality() { - try { - ythrow TFileError() << "1"; - UNIT_ASSERT(false); - } catch (const TIoException&) { - } catch (...) { - UNIT_ASSERT(false); - } - - try { - ythrow TFileError() << 1; - UNIT_ASSERT(false); - } catch (const TSystemError&) { - } catch (...) { - UNIT_ASSERT(false); - } - - try { - ythrow TFileError() << '1'; - UNIT_ASSERT(false); - } catch (const yexception&) { - } catch (...) { - UNIT_ASSERT(false); - } - - try { - ythrow TFileError() << 1.0; - UNIT_ASSERT(false); - } catch (const TFileError&) { - } catch (...) { - UNIT_ASSERT(false); - } - } - - inline void TestFormat1() { - try { - throw yexception() << 1 << " qw " << 12.1; - UNIT_ASSERT(false); - } catch (...) { + inline void TestVirtualInheritance() { + TStringStream ss; + + OUTS = &ss; + + class TA { + public: + inline TA() { + *OUTS << "A"; + } + }; + + class TB { + public: + inline TB() { + *OUTS << "B"; + } + }; + + class TC: public virtual TB, public virtual TA { + public: + inline TC() { + *OUTS << "C"; + } + }; + + class TD: public virtual TA { + public: + inline TD() { + *OUTS << "D"; + } + }; + + class TE: public TC, public TD { + public: + inline TE() { + *OUTS << "E"; + } + }; + + TE e; + + UNIT_ASSERT_EQUAL(ss.Str(), "BACDE"); + } + + inline void TestVirtuality() { + try { + ythrow TFileError() << "1"; + UNIT_ASSERT(false); + } catch (const TIoException&) { + } catch (...) { + UNIT_ASSERT(false); + } + + try { + ythrow TFileError() << 1; + UNIT_ASSERT(false); + } catch (const TSystemError&) { + } catch (...) { + UNIT_ASSERT(false); + } + + try { + ythrow TFileError() << '1'; + UNIT_ASSERT(false); + } catch (const yexception&) { + } catch (...) { + UNIT_ASSERT(false); + } + + try { + ythrow TFileError() << 1.0; + UNIT_ASSERT(false); + } catch (const TFileError&) { + } catch (...) { + UNIT_ASSERT(false); + } + } + + inline void TestFormat1() { + try { + throw yexception() << 1 << " qw " << 12.1; + UNIT_ASSERT(false); + } catch (...) { const TString err = CurrentExceptionMessage(); - - UNIT_ASSERT(err.Contains("1 qw 12.1")); - } - } - + + UNIT_ASSERT(err.Contains("1 qw 12.1")); + } + } + static inline void CheckCurrentExceptionContains(const char* message) { TString err = CurrentExceptionMessage(); SubstGlobal(err, '\\', '/'); // remove backslashes from path in message UNIT_ASSERT(err.Contains(message)); } - inline void TestRaise1() { - try { - Throw2DontMove(); - UNIT_ASSERT(false); - } catch (...) { + inline void TestRaise1() { + try { + Throw2DontMove(); + UNIT_ASSERT(false); + } catch (...) { CheckCurrentExceptionContains("util/generic/yexception_ut.cpp:8: 1 qw 12.1"); - } - } - - inline void TestException() { - ythrow yexception() << "blablabla"; - } - - inline void TestLineInfo() { - try { - Throw1DontMove(); + } + } + + inline void TestException() { + ythrow yexception() << "blablabla"; + } + + inline void TestLineInfo() { + try { + Throw1DontMove(); UNIT_ASSERT(false); - } catch (...) { + } catch (...) { CheckCurrentExceptionContains("util/generic/yexception_ut.cpp:4: blabla"); - - throw; - } - } - - //! tests propagation of an exception through C code - //! @note on some platforms, for example GCC on 32-bit Linux without -fexceptions option, - //! throwing an exception from a C++ callback through C code aborts program - inline void TestMixedCode() { - const int N = 26082009; - try { - TestCallback(&CallbackFun, N); - UNIT_ASSERT(false); - } catch (int i) { - UNIT_ASSERT_VALUES_EQUAL(i, N); + + throw; } - } + } + + //! tests propagation of an exception through C code + //! @note on some platforms, for example GCC on 32-bit Linux without -fexceptions option, + //! throwing an exception from a C++ callback through C code aborts program + inline void TestMixedCode() { + const int N = 26082009; + try { + TestCallback(&CallbackFun, N); + UNIT_ASSERT(false); + } catch (int i) { + UNIT_ASSERT_VALUES_EQUAL(i, N); + } + } void TestMacroOverload() { try { @@ -347,7 +347,7 @@ private: } } //Test when the caught exception is rethrown with throw; . - //This test is different from the previous one because of the interaction with cxxabi specifics. + //This test is different from the previous one because of the interaction with cxxabi specifics. try { throw std::bad_alloc(); } catch (...) { @@ -387,6 +387,6 @@ private: } } } -}; - -UNIT_TEST_SUITE_REGISTRATION(TExceptionTest); +}; + +UNIT_TEST_SUITE_REGISTRATION(TExceptionTest); diff --git a/util/generic/yexception_ut.h b/util/generic/yexception_ut.h index 01dd288375..acf6f27e99 100644 --- a/util/generic/yexception_ut.h +++ b/util/generic/yexception_ut.h @@ -4,10 +4,10 @@ extern "C" { #endif - typedef void (*TCallbackFun)(int); + typedef void (*TCallbackFun)(int); - //! just calls callback with parameter @c i - void TestCallback(TCallbackFun f, int i); + //! just calls callback with parameter @c i + void TestCallback(TCallbackFun f, int i); #ifdef __cplusplus } diff --git a/util/generic/ylimits.cpp b/util/generic/ylimits.cpp index e1f28178ad..bcacf965e3 100644 --- a/util/generic/ylimits.cpp +++ b/util/generic/ylimits.cpp @@ -1 +1 @@ -#include "ylimits.h" +#include "ylimits.h" diff --git a/util/generic/ylimits.h b/util/generic/ylimits.h index 7982f9e7ed..fe42b4dfc0 100644 --- a/util/generic/ylimits.h +++ b/util/generic/ylimits.h @@ -1,20 +1,20 @@ #pragma once - -#include <limits> - + +#include <limits> + #if defined(max) || defined(min) - #error "stop defining 'min' and 'max' macros, evil people" + #error "stop defining 'min' and 'max' macros, evil people" #endif -template <class T> +template <class T> static constexpr T Max() noexcept { return std::numeric_limits<T>::max(); -} - -template <class T> +} + +template <class T> static constexpr T Min() noexcept { return std::numeric_limits<T>::min(); -} +} namespace NPrivate { struct TMax { @@ -33,11 +33,11 @@ namespace NPrivate { } static constexpr ::NPrivate::TMax Max() noexcept { - return {}; + return {}; } static constexpr ::NPrivate::TMin Min() noexcept { - return {}; + return {}; } namespace NPrivate { diff --git a/util/generic/ylimits_ut.cpp b/util/generic/ylimits_ut.cpp index c381fb2a6f..f1b3c6858c 100644 --- a/util/generic/ylimits_ut.cpp +++ b/util/generic/ylimits_ut.cpp @@ -1,147 +1,147 @@ #include "cast.h" -#include "ylimits.h" - +#include "ylimits.h" + #include <library/cpp/testing/unittest/registar.h> - -#include <util/string/cast.h> -#include <util/system/valgrind.h> - -class TLimitTest: public TTestBase { - UNIT_TEST_SUITE(TLimitTest); - UNIT_TEST(TestLimits); - UNIT_TEST(TestNan); + +#include <util/string/cast.h> +#include <util/system/valgrind.h> + +class TLimitTest: public TTestBase { + UNIT_TEST_SUITE(TLimitTest); + UNIT_TEST(TestLimits); + UNIT_TEST(TestNan); UNIT_TEST(TestMaxDouble); - UNIT_TEST_SUITE_END(); - -protected: - void TestLimits(); - void TestNan(); + UNIT_TEST_SUITE_END(); + +protected: + void TestLimits(); + void TestNan(); void TestMaxDouble(); -}; - -UNIT_TEST_SUITE_REGISTRATION(TLimitTest); - -#define CHECK_COND(X) UNIT_ASSERT(X) - -static inline bool ValidSignInfo(bool, bool) { - return true; -} - -template <class T> -static inline bool ValidSignInfo(bool limitIsSigned, const T&) { - return limitIsSigned && IsNegative(T(-1)) || !limitIsSigned && !IsNegative(T(-1)); -} - -template <class T> -static inline bool TestIntegralLimits(const T&, bool unknownSign = true, bool isSigned = true) { +}; + +UNIT_TEST_SUITE_REGISTRATION(TLimitTest); + +#define CHECK_COND(X) UNIT_ASSERT(X) + +static inline bool ValidSignInfo(bool, bool) { + return true; +} + +template <class T> +static inline bool ValidSignInfo(bool limitIsSigned, const T&) { + return limitIsSigned && IsNegative(T(-1)) || !limitIsSigned && !IsNegative(T(-1)); +} + +template <class T> +static inline bool TestIntegralLimits(const T&, bool unknownSign = true, bool isSigned = true) { using lim = std::numeric_limits<T>; - - CHECK_COND(lim::is_specialized); - CHECK_COND(lim::is_integer); - CHECK_COND(lim::min() < lim::max()); - CHECK_COND((unknownSign && ((lim::is_signed && (lim::min() != 0)) || (!lim::is_signed && (lim::min() == 0)))) || - (!unknownSign && ((lim::is_signed && isSigned) || (!lim::is_signed && !isSigned)))); - + + CHECK_COND(lim::is_specialized); + CHECK_COND(lim::is_integer); + CHECK_COND(lim::min() < lim::max()); + CHECK_COND((unknownSign && ((lim::is_signed && (lim::min() != 0)) || (!lim::is_signed && (lim::min() == 0)))) || + (!unknownSign && ((lim::is_signed && isSigned) || (!lim::is_signed && !isSigned)))); + T min = Min(); UNIT_ASSERT_EQUAL(lim::min(), min); T max = Max(); UNIT_ASSERT_EQUAL(lim::max(), max); - if (unknownSign) { - CHECK_COND(ValidSignInfo(lim::is_signed, T())); - } - - return true; -} - -template <class T> -static inline bool TestSignedIntegralLimits(const T& val) { - return TestIntegralLimits(val, false, true); -} - -template <class T> -static inline bool TestUnsignedIntegralLimits(const T& val) { - return TestIntegralLimits(val, false, false); -} - -template <class T> -static inline bool TestFloatLimits(const T&) { + if (unknownSign) { + CHECK_COND(ValidSignInfo(lim::is_signed, T())); + } + + return true; +} + +template <class T> +static inline bool TestSignedIntegralLimits(const T& val) { + return TestIntegralLimits(val, false, true); +} + +template <class T> +static inline bool TestUnsignedIntegralLimits(const T& val) { + return TestIntegralLimits(val, false, false); +} + +template <class T> +static inline bool TestFloatLimits(const T&) { using lim = std::numeric_limits<T>; - - CHECK_COND(lim::is_specialized); - CHECK_COND(!lim::is_modulo); - CHECK_COND(!lim::is_integer); - CHECK_COND(lim::is_signed); - - CHECK_COND(lim::max() > 1000); - CHECK_COND(lim::min() > 0); - CHECK_COND(lim::min() < 0.001); - CHECK_COND(lim::epsilon() > 0); - - if (lim::is_iec559) { - CHECK_COND(lim::has_infinity); - CHECK_COND(lim::has_quiet_NaN); - CHECK_COND(lim::has_signaling_NaN); - } - - if (lim::has_infinity) { - const T infinity = lim::infinity(); - - CHECK_COND(infinity > lim::max()); - CHECK_COND(-infinity < -lim::max()); - } - - return true; -} - -template <class T> -static inline bool TestNan(const T&) { + + CHECK_COND(lim::is_specialized); + CHECK_COND(!lim::is_modulo); + CHECK_COND(!lim::is_integer); + CHECK_COND(lim::is_signed); + + CHECK_COND(lim::max() > 1000); + CHECK_COND(lim::min() > 0); + CHECK_COND(lim::min() < 0.001); + CHECK_COND(lim::epsilon() > 0); + + if (lim::is_iec559) { + CHECK_COND(lim::has_infinity); + CHECK_COND(lim::has_quiet_NaN); + CHECK_COND(lim::has_signaling_NaN); + } + + if (lim::has_infinity) { + const T infinity = lim::infinity(); + + CHECK_COND(infinity > lim::max()); + CHECK_COND(-infinity < -lim::max()); + } + + return true; +} + +template <class T> +static inline bool TestNan(const T&) { using lim = std::numeric_limits<T>; - - if (lim::has_quiet_NaN) { - const T qnan = lim::quiet_NaN(); - - CHECK_COND(!(qnan == 42)); - CHECK_COND(!(qnan == qnan)); - CHECK_COND(qnan != 42); - CHECK_COND(qnan != qnan); - } - - return true; -} - -void TLimitTest::TestLimits() { - UNIT_ASSERT(TestIntegralLimits(bool())); - UNIT_ASSERT(TestIntegralLimits(char())); + + if (lim::has_quiet_NaN) { + const T qnan = lim::quiet_NaN(); + + CHECK_COND(!(qnan == 42)); + CHECK_COND(!(qnan == qnan)); + CHECK_COND(qnan != 42); + CHECK_COND(qnan != qnan); + } + + return true; +} + +void TLimitTest::TestLimits() { + UNIT_ASSERT(TestIntegralLimits(bool())); + UNIT_ASSERT(TestIntegralLimits(char())); using signed_char = signed char; - UNIT_ASSERT(TestSignedIntegralLimits(signed_char())); + UNIT_ASSERT(TestSignedIntegralLimits(signed_char())); using unsigned_char = unsigned char; - UNIT_ASSERT(TestUnsignedIntegralLimits(unsigned_char())); - UNIT_ASSERT(TestSignedIntegralLimits(short())); + UNIT_ASSERT(TestUnsignedIntegralLimits(unsigned_char())); + UNIT_ASSERT(TestSignedIntegralLimits(short())); using unsigned_short = unsigned short; - UNIT_ASSERT(TestUnsignedIntegralLimits(unsigned_short())); - UNIT_ASSERT(TestSignedIntegralLimits(int())); + UNIT_ASSERT(TestUnsignedIntegralLimits(unsigned_short())); + UNIT_ASSERT(TestSignedIntegralLimits(int())); using unsigned_int = unsigned int; - UNIT_ASSERT(TestUnsignedIntegralLimits(unsigned_int())); - UNIT_ASSERT(TestSignedIntegralLimits(long())); + UNIT_ASSERT(TestUnsignedIntegralLimits(unsigned_int())); + UNIT_ASSERT(TestSignedIntegralLimits(long())); using unsigned_long = unsigned long; - UNIT_ASSERT(TestUnsignedIntegralLimits(unsigned_long())); + UNIT_ASSERT(TestUnsignedIntegralLimits(unsigned_long())); using long_long = long long; - UNIT_ASSERT(TestSignedIntegralLimits(long_long())); + UNIT_ASSERT(TestSignedIntegralLimits(long_long())); using unsigned_long_long = unsigned long long; - UNIT_ASSERT(TestUnsignedIntegralLimits(unsigned_long_long())); - UNIT_ASSERT(TestFloatLimits(float())); - UNIT_ASSERT(TestFloatLimits(double())); + UNIT_ASSERT(TestUnsignedIntegralLimits(unsigned_long_long())); + UNIT_ASSERT(TestFloatLimits(float())); + UNIT_ASSERT(TestFloatLimits(double())); using long_double = long double; UNIT_ASSERT(RUNNING_ON_VALGRIND || TestFloatLimits(long_double())); -} - -void TLimitTest::TestNan() { - UNIT_ASSERT(::TestNan(float())); - UNIT_ASSERT(::TestNan(double())); +} + +void TLimitTest::TestNan() { + UNIT_ASSERT(::TestNan(float())); + UNIT_ASSERT(::TestNan(double())); using long_double = long double; - UNIT_ASSERT(::TestNan(long_double())); -} + UNIT_ASSERT(::TestNan(long_double())); +} void TLimitTest::TestMaxDouble() { UNIT_ASSERT_VALUES_EQUAL(MaxCeil<i8>(), 127.0); diff --git a/util/generic/ymath.cpp b/util/generic/ymath.cpp index 3355f8fc73..31270728f4 100644 --- a/util/generic/ymath.cpp +++ b/util/generic/ymath.cpp @@ -36,9 +36,9 @@ double LogGammaImpl(double x) { static constexpr double coeff3 = -1.0 / 360.0; static constexpr double coeff1 = 1.0 / 12.0; - if ((x == 1.0) || (x == 2.0)) { + if ((x == 1.0) || (x == 2.0)) { return 0.0; // 0! = 1 - } + } double bonus = 0.0; while (x < 3.0) { bonus -= log(x); diff --git a/util/generic/ymath.h b/util/generic/ymath.h index 5f5f5df210..9ff9ae2abe 100644 --- a/util/generic/ymath.h +++ b/util/generic/ymath.h @@ -1,12 +1,12 @@ #pragma once - + #include <util/system/yassert.h> #include <util/system/defaults.h> - + #include <cmath> #include <cfloat> #include <cstdlib> - + #include "typetraits.h" #include "utility.h" @@ -19,7 +19,7 @@ constexpr double M_LN2_INV = M_LOG2E; // 1 / ln(2) == log2(e) */ template <class T> constexpr T Abs(T value) { - return std::abs(value); + return std::abs(value); } /** @@ -29,7 +29,7 @@ constexpr T Abs(T value) { inline double Log2(double value) { return log(value) * M_LN2_INV; } - + /** * @returns Base 2 logarithm of the provided * floating point value. @@ -41,7 +41,7 @@ inline float Log2(float value) { /** * @returns Base 2 logarithm of the provided integral value. */ -template <class T> +template <class T> inline std::enable_if_t<std::is_integral<T>::value, double> Log2(T value) { return Log2(static_cast<double>(value)); @@ -51,11 +51,11 @@ Log2(T value) { double Exp2(double); float Exp2f(float); -template <class T> +template <class T> static constexpr T Sqr(const T t) noexcept { - return t * t; -} - + return t * t; +} + inline double Sigmoid(double x) { return 1.0 / (1.0 + std::exp(-x)); } @@ -64,33 +64,33 @@ inline float Sigmoid(float x) { return 1.0f / (1.0f + std::exp(-x)); } -static inline bool IsFinite(double f) { -#if defined(isfinite) - return isfinite(f); -#elif defined(_win_) +static inline bool IsFinite(double f) { +#if defined(isfinite) + return isfinite(f); +#elif defined(_win_) return _finite(f) != 0; -#elif defined(_darwin_) - return isfinite(f); -#elif defined(__GNUC__) - return __builtin_isfinite(f); -#elif defined(_STLP_VENDOR_STD) - return _STLP_VENDOR_STD::isfinite(f); -#else - return std::isfinite(f); -#endif -} - -static inline bool IsNan(double f) { -#if defined(_win_) +#elif defined(_darwin_) + return isfinite(f); +#elif defined(__GNUC__) + return __builtin_isfinite(f); +#elif defined(_STLP_VENDOR_STD) + return _STLP_VENDOR_STD::isfinite(f); +#else + return std::isfinite(f); +#endif +} + +static inline bool IsNan(double f) { +#if defined(_win_) return _isnan(f) != 0; -#else +#else return std::isnan(f); -#endif -} - -inline bool IsValidFloat(double f) { - return IsFinite(f) && !IsNan(f); -} +#endif +} + +inline bool IsValidFloat(double f) { + return IsFinite(f) && !IsNan(f); +} #ifdef _MSC_VER double Erf(double x); @@ -104,27 +104,27 @@ inline double Erf(double x) { * @returns Natural logarithm of the absolute value * of the gamma function of provided argument. */ -inline double LogGamma(double x) noexcept { -#if defined(_glibc_) - int sign; - - (void)sign; - - return lgamma_r(x, &sign); -#elif defined(__GNUC__) - return __builtin_lgamma(x); -#elif defined(_unix_) +inline double LogGamma(double x) noexcept { +#if defined(_glibc_) + int sign; + + (void)sign; + + return lgamma_r(x, &sign); +#elif defined(__GNUC__) + return __builtin_lgamma(x); +#elif defined(_unix_) return lgamma(x); #else - extern double LogGammaImpl(double); - return LogGammaImpl(x); + extern double LogGammaImpl(double); + return LogGammaImpl(x); #endif -} +} /** * @returns x^n for integer n, n >= 0. */ -template <class T, class Int> +template <class T, class Int> T Power(T x, Int n) { static_assert(std::is_integral<Int>::value, "only integer powers are supported"); Y_ASSERT(n >= 0); @@ -179,7 +179,7 @@ namespace NUtilMathPrivate { template <> struct TCeilDivImpl<true> { - template <class T> + template <class T> static inline T Do(T x, T y) noexcept { return x / y + (((x < 0) ^ (y > 0)) && (x % y)); } @@ -187,7 +187,7 @@ namespace NUtilMathPrivate { template <> struct TCeilDivImpl<false> { - template <class T> + template <class T> static inline T Do(T x, T y) noexcept { auto quot = x / y; return (x % y) ? (quot + 1) : quot; diff --git a/util/generic/ymath_ut.cpp b/util/generic/ymath_ut.cpp index 934137b056..29190b55eb 100644 --- a/util/generic/ymath_ut.cpp +++ b/util/generic/ymath_ut.cpp @@ -1,132 +1,132 @@ #include "bitops.h" -#include "ymath.h" - +#include "ymath.h" + #include <library/cpp/testing/unittest/registar.h> - + #include <util/stream/output.h> -#include <util/datetime/cputimer.h> - -#include <limits> - -template <class T> +#include <util/datetime/cputimer.h> + +#include <limits> + +template <class T> static inline T SlowClp2(T t) noexcept { Y_ASSERT(t > 0); - + T ret = 1; - + while (ret < t) { ret *= 2; - } - + } + return ret; -} - -class TMathTest: public TTestBase { - UNIT_TEST_SUITE(TMathTest); - UNIT_TEST(TestClp2) - UNIT_TEST(TestClpSimple) - UNIT_TEST(TestSqr) - UNIT_TEST(TestLog2) - UNIT_TEST(ValueBitCount) - UNIT_TEST(TestErf); - UNIT_TEST(TestLogGamma); - UNIT_TEST(TestIsValidFloat); +} + +class TMathTest: public TTestBase { + UNIT_TEST_SUITE(TMathTest); + UNIT_TEST(TestClp2) + UNIT_TEST(TestClpSimple) + UNIT_TEST(TestSqr) + UNIT_TEST(TestLog2) + UNIT_TEST(ValueBitCount) + UNIT_TEST(TestErf); + UNIT_TEST(TestLogGamma); + UNIT_TEST(TestIsValidFloat); UNIT_TEST(TestAbs); UNIT_TEST(TestPower); UNIT_TEST(TestSigmoid); UNIT_TEST(TestCeilDiv); - UNIT_TEST_SUITE_END(); - -private: - void TestClp2(); - void TestSqr(); - void TestErf(); - void TestLogGamma(); + UNIT_TEST_SUITE_END(); + +private: + void TestClp2(); + void TestSqr(); + void TestErf(); + void TestLogGamma(); void TestAbs(); void TestPower(); void TestSigmoid(); void TestCeilDiv(); - - inline void TestIsValidFloat() { - UNIT_ASSERT(IsValidFloat(-Max<double>() / 2.)); - } - - inline void TestClpSimple() { - UNIT_ASSERT_EQUAL(FastClp2<ui32>(12), 16); - UNIT_ASSERT_EQUAL(FastClp2<ui16>(11), 16); - UNIT_ASSERT_EQUAL(FastClp2<ui8>(10), 16); - - UNIT_ASSERT_EQUAL(FastClp2<ui32>(15), 16); - UNIT_ASSERT_EQUAL(FastClp2<ui32>(16), 16); - UNIT_ASSERT_EQUAL(FastClp2<ui32>(17), 32); - } - - inline void TestLog2() { - UNIT_ASSERT_DOUBLES_EQUAL(Log2(2.0), 1.0, 1e-10); + + inline void TestIsValidFloat() { + UNIT_ASSERT(IsValidFloat(-Max<double>() / 2.)); + } + + inline void TestClpSimple() { + UNIT_ASSERT_EQUAL(FastClp2<ui32>(12), 16); + UNIT_ASSERT_EQUAL(FastClp2<ui16>(11), 16); + UNIT_ASSERT_EQUAL(FastClp2<ui8>(10), 16); + + UNIT_ASSERT_EQUAL(FastClp2<ui32>(15), 16); + UNIT_ASSERT_EQUAL(FastClp2<ui32>(16), 16); + UNIT_ASSERT_EQUAL(FastClp2<ui32>(17), 32); + } + + inline void TestLog2() { + UNIT_ASSERT_DOUBLES_EQUAL(Log2(2.0), 1.0, 1e-10); UNIT_ASSERT_DOUBLES_EQUAL(Log2(2ull), 1.0, 1e-10); UNIT_ASSERT_DOUBLES_EQUAL(Log2(2.0f), 1.0f, 1e-7f); - } - - inline void ValueBitCount() { - UNIT_ASSERT_VALUES_EQUAL(GetValueBitCount(1), 1u); - UNIT_ASSERT_VALUES_EQUAL(GetValueBitCount(2), 2u); - UNIT_ASSERT_VALUES_EQUAL(GetValueBitCount(3), 2u); - UNIT_ASSERT_VALUES_EQUAL(GetValueBitCount(257), 9u); - } -}; - -UNIT_TEST_SUITE_REGISTRATION(TMathTest); - -void TMathTest::TestSqr() { - UNIT_ASSERT_EQUAL(Sqr(2), 4); - UNIT_ASSERT_EQUAL(Sqr(2.0), 4.0); -} - -void TMathTest::TestClp2() { + } + + inline void ValueBitCount() { + UNIT_ASSERT_VALUES_EQUAL(GetValueBitCount(1), 1u); + UNIT_ASSERT_VALUES_EQUAL(GetValueBitCount(2), 2u); + UNIT_ASSERT_VALUES_EQUAL(GetValueBitCount(3), 2u); + UNIT_ASSERT_VALUES_EQUAL(GetValueBitCount(257), 9u); + } +}; + +UNIT_TEST_SUITE_REGISTRATION(TMathTest); + +void TMathTest::TestSqr() { + UNIT_ASSERT_EQUAL(Sqr(2), 4); + UNIT_ASSERT_EQUAL(Sqr(2.0), 4.0); +} + +void TMathTest::TestClp2() { for (ui8 i = 1; i < 127; ++i) { - UNIT_ASSERT_EQUAL(SlowClp2(i), FastClp2(i)); - } - + UNIT_ASSERT_EQUAL(SlowClp2(i), FastClp2(i)); + } + for (ui16 i = 1; i < 255; ++i) { - UNIT_ASSERT_EQUAL(SlowClp2(i), FastClp2(i)); - } - + UNIT_ASSERT_EQUAL(SlowClp2(i), FastClp2(i)); + } + for (ui32 i = 1; i < 255; ++i) { - UNIT_ASSERT_EQUAL(SlowClp2(i), FastClp2(i)); - } - + UNIT_ASSERT_EQUAL(SlowClp2(i), FastClp2(i)); + } + for (ui64 i = 1; i < 255; ++i) { - UNIT_ASSERT_EQUAL(SlowClp2(i), FastClp2(i)); - } - - if (0) { - { - TFuncTimer timer("fast"); - size_t ret = 0; - - for (size_t i = 0; i < 10000000; ++i) { - ret += FastClp2(i); - } - - Cerr << ret << Endl; - } - - { - TFuncTimer timer("slow"); - size_t ret = 0; - - for (size_t i = 0; i < 10000000; ++i) { - ret += SlowClp2(i); - } - - Cerr << ret << Endl; - } - } -} + UNIT_ASSERT_EQUAL(SlowClp2(i), FastClp2(i)); + } + + if (0) { + { + TFuncTimer timer("fast"); + size_t ret = 0; + + for (size_t i = 0; i < 10000000; ++i) { + ret += FastClp2(i); + } + + Cerr << ret << Endl; + } + + { + TFuncTimer timer("slow"); + size_t ret = 0; + + for (size_t i = 0; i < 10000000; ++i) { + ret += SlowClp2(i); + } + + Cerr << ret << Endl; + } + } +} void TMathTest::TestErf() { static const double a = -5.0; - static const double b = 5.0; + static const double b = 5.0; static const int n = 50; static const double step = (b - a) / n; @@ -136,12 +136,12 @@ void TMathTest::TestErf() { -0.9999779, -0.9999250, -0.9997640, -0.9993115, -0.9981372, -0.9953223, -0.9890905, -0.9763484, -0.9522851, -0.9103140, -0.8427008, -0.7421010, -0.6038561, -0.4283924, -0.2227026, - 0.0000000, - 0.2227026, 0.4283924, 0.6038561, 0.7421010, 0.8427008, - 0.9103140, 0.9522851, 0.9763484, 0.9890905, 0.9953223, - 0.9981372, 0.9993115, 0.9997640, 0.9999250, 0.9999779, - 0.9999940, 0.9999985, 0.9999996, 0.9999999, 1.0000000, - 1.0000000, 1.0000000, 1.0000000, 1.0000000, 1.0000000}; + 0.0000000, + 0.2227026, 0.4283924, 0.6038561, 0.7421010, 0.8427008, + 0.9103140, 0.9522851, 0.9763484, 0.9890905, 0.9953223, + 0.9981372, 0.9993115, 0.9997640, 0.9999250, 0.9999779, + 0.9999940, 0.9999985, 0.9999996, 0.9999999, 1.0000000, + 1.0000000, 1.0000000, 1.0000000, 1.0000000, 1.0000000}; double x = a; for (int i = 0; i <= n; ++i, x += step) { @@ -154,7 +154,7 @@ void TMathTest::TestLogGamma() { double curVal = 0.0; for (int i = 1; i <= 20; i++) { curVal += log((double)i); - UNIT_ASSERT_DOUBLES_EQUAL(curVal, LogGamma((double)(i + 1)), 1e-6); + UNIT_ASSERT_DOUBLES_EQUAL(curVal, LogGamma((double)(i + 1)), 1e-6); } curVal = log(M_PI) / 2.0; for (int i = 1; i <= 20; i++) { |