diff options
author | Nat Goodspeed <nat@lindenlab.com> | 2022-06-18 11:53:57 -0400 |
---|---|---|
committer | Nat Goodspeed <nat@lindenlab.com> | 2022-08-22 20:39:37 -0400 |
commit | c0f709b637d800fe07fb265c8ab6f28080994224 (patch) | |
tree | f367fea3f47f0555a3e60ea7f294bb2a3f68dc94 /indra | |
parent | 9dba9f80f4d40ec12a735ddbb66a9d103a959ece (diff) |
DRTVWR-564: Add LL::apply(): call function, passing args from tuple.
This anticipates C++17's std::apply(), and in fact once we detect C++17, we'll
just use that. But in C++14 we must still provide our own implementation.
(cherry picked from commit dc2e2cd76f387ea6e80787fb94adcbc269cd1f25)
Diffstat (limited to 'indra')
-rw-r--r-- | indra/llcommon/apply.h | 51 |
1 files changed, 51 insertions, 0 deletions
diff --git a/indra/llcommon/apply.h b/indra/llcommon/apply.h new file mode 100644 index 0000000000..ef4a8fd68b --- /dev/null +++ b/indra/llcommon/apply.h @@ -0,0 +1,51 @@ +/** + * @file apply.h + * @author Nat Goodspeed + * @date 2022-06-18 + * @brief C++14 version of std::apply() + * + * $LicenseInfo:firstyear=2022&license=viewerlgpl$ + * Copyright (c) 2022, Linden Research, Inc. + * $/LicenseInfo$ + */ + +#if ! defined(LL_APPLY_H) +#define LL_APPLY_H + +#include <tuple> + +namespace LL +{ + +#if __cplusplus >= 201703L + +// C++17 implementation +using std::apply; + +#else // C++14 + +// Derived from https://stackoverflow.com/a/20441189 +// and https://en.cppreference.com/w/cpp/utility/apply +template <typename CALLABLE, typename TUPLE, std::size_t... I> +auto apply_impl(CALLABLE&& func, TUPLE&& args, std::index_sequence<I...>) +{ + // call func(unpacked args) + return std::forward<CALLABLE>(func)(std::move(std::get<I>(args))...); +} + +template <typename CALLABLE, typename... ARGS> +auto apply(CALLABLE&& func, std::tuple<ARGS...>&& args) +{ + // std::index_sequence_for is the magic sauce here, generating an argument + // pack of indexes for each entry in args. apply_impl() can then pass + // those to std::get() to unpack args into individual arguments. + return apply_impl(std::forward<CALLABLE>(func), + std::forward<std::tuple<ARGS...>>(args), + std::index_sequence_for<ARGS...>{}); +} + +#endif // C++14 + +} // namespace LL + +#endif /* ! defined(LL_APPLY_H) */ |