xref: /openbmc/telemetry/src/utils/transform.hpp (revision 7e114c04)
1 #pragma once
2 
3 #include <algorithm>
4 #include <iterator>
5 
6 namespace utils
7 {
8 namespace detail
9 {
10 
11 template <class T>
12 concept has_member_reserve = requires(T t) { t.reserve(size_t{}); };
13 
14 } // namespace detail
15 
16 template <template <class, class...> class R, class Container, class Functor>
transform(const Container & container,Functor && f)17 inline auto transform(const Container& container, Functor&& f)
18 {
19     auto result = R<decltype(f(*container.begin()))>{};
20 
21     if constexpr (detail::has_member_reserve<decltype(result)>)
22     {
23         result.reserve(container.size());
24     }
25 
26     std::transform(container.begin(), container.end(),
27                    std::inserter(result, result.end()),
28                    std::forward<Functor>(f));
29 
30     return result;
31 }
32 
33 template <template <class, class...> class Container, class Functor,
34           class... Args>
transform(const Container<Args...> & container,Functor && f)35 inline auto transform(const Container<Args...>& container, Functor&& f)
36 {
37     return transform<Container, Container<Args...>, Functor>(
38         container, std::forward<Functor>(f));
39 }
40 
41 } // namespace utils
42