Date: Mon, 15 Jul 2019 13:27:20 +0100

Rather than providing an overload of std::apply, I think it would make more

sense to provide implementations of std::get and std::tuple_size for

std::integer_sequence, considering an integer sequence is also an

array-like "collection" that can be iterated through at compile-time.

This has the advantage of not only ending up with the same syntax as you

mentioned, but also it "future-proofs" std::integer_sequence and its

relatives, in case a new function is added to the STL.

On Sat, 13 Jul 2019, 22:55 Jordi Vilar via Std-Proposals, <

std-proposals_at_[hidden]> wrote:

> Hi all,

>

> I would like to propose a very simple addition to the standard library in

> order to simplify variadic parameter pack expansion, and before writing a

> formal proposal I just wanted to share it in order to get feedback.

>

> Typically, expanding indices sequences require writing a dedicated helper

> wrapper. This is tedious and offers no value at all. A Search through the

> Internet shows that similar approaches have been informally proposed, for

> instance, in [stack overflow](

> https://stackoverflow.com/questions/47210956/c17-multiple-parameter-pack-expansion

> )

>

> The proposal is about having a generic, reusable wrapper for expanding

> integer sequences similar to the std::apply facility for expanding tuples,

> considering the following:

> - simplify the common case of expanding an index sequence with a provided

> lambda

> - expansion must be usable as literal values to enable template

> instantiation (for instance, can be used to call std::get<index>(x)...)

> - support for non-sequential index sequences, and integral types other

> than std::size_t

> - syntax similar to std::apply and std::visit

> - the name could be just std::apply as a new overload, as this is

> conceptually the same as expanding a tuple but for integral constants

>

> The proposal is then:

>

> /// Invoke the Callable object function with a sequence of indices

> /// \param[in] function A callable object that will be invoked with

> std::integral_constant arguments instantiated for each index in the \a

> sequence integer_sequence

> /// \param[in] sequence A std::integer_sequence to be expanded

> /// \return The \a apply helper function returns whatever the provided

> callable object returns

> namespace std

> {

> template<typename F, typename T, T... indices>

> constexpr decltype(auto) apply(F&& function, [[maybe_unused]]

> std::integer_sequence<T, indices...> sequence)

> {

> return function(std::integral_constant<T, indices>{}...);

> }

> }

>

> The idea of having arguments encoded as std::integral_constant allows for

> using them not only as constexpr but also as template arguments.

>

> This simple helper function could allow us to write, for instance:

>

> /// performs the addition of two arrays of arithmetic types

> template<typename T, std::size_t N>

> auto operator +(const std::array<T, N>& lhs, const std::array<T, N>& rhs)

> -> std::enable_if_t<std::is_arithmetic_v<T>, std::array<T, N>>

> {

> return std::apply([&](auto... indices) { return std::array<T, N>{

> (std::get<indices>(lhs) + std::get<indices>(rhs))... }; },

> std::make_index_sequence<N>{});

> }

>

> int main(int argc, char** argv)

> {

> auto result = std::array{1, 2, 3} + std::array{5, 4, 3};

> apply([&](auto... indices) { (std::cout << ... << result[indices]); },

> std::make_index_sequence<3>{});

> }

>

> Even the current std::apply function for tuples could be rewriten on top

> of this proposal.

>

> No language changes are required. It can be implemented on top of C++17

> and C++14.

>

> Waiting for your feedback,

>

> Jordi

> --

> Std-Proposals mailing list

> Std-Proposals_at_[hidden]

> http://lists.isocpp.org/mailman/listinfo.cgi/std-proposals

>

sense to provide implementations of std::get and std::tuple_size for

std::integer_sequence, considering an integer sequence is also an

array-like "collection" that can be iterated through at compile-time.

This has the advantage of not only ending up with the same syntax as you

mentioned, but also it "future-proofs" std::integer_sequence and its

relatives, in case a new function is added to the STL.

On Sat, 13 Jul 2019, 22:55 Jordi Vilar via Std-Proposals, <

std-proposals_at_[hidden]> wrote:

> Hi all,

>

> I would like to propose a very simple addition to the standard library in

> order to simplify variadic parameter pack expansion, and before writing a

> formal proposal I just wanted to share it in order to get feedback.

>

> Typically, expanding indices sequences require writing a dedicated helper

> wrapper. This is tedious and offers no value at all. A Search through the

> Internet shows that similar approaches have been informally proposed, for

> instance, in [stack overflow](

> https://stackoverflow.com/questions/47210956/c17-multiple-parameter-pack-expansion

> )

>

> The proposal is about having a generic, reusable wrapper for expanding

> integer sequences similar to the std::apply facility for expanding tuples,

> considering the following:

> - simplify the common case of expanding an index sequence with a provided

> lambda

> - expansion must be usable as literal values to enable template

> instantiation (for instance, can be used to call std::get<index>(x)...)

> - support for non-sequential index sequences, and integral types other

> than std::size_t

> - syntax similar to std::apply and std::visit

> - the name could be just std::apply as a new overload, as this is

> conceptually the same as expanding a tuple but for integral constants

>

> The proposal is then:

>

> /// Invoke the Callable object function with a sequence of indices

> /// \param[in] function A callable object that will be invoked with

> std::integral_constant arguments instantiated for each index in the \a

> sequence integer_sequence

> /// \param[in] sequence A std::integer_sequence to be expanded

> /// \return The \a apply helper function returns whatever the provided

> callable object returns

> namespace std

> {

> template<typename F, typename T, T... indices>

> constexpr decltype(auto) apply(F&& function, [[maybe_unused]]

> std::integer_sequence<T, indices...> sequence)

> {

> return function(std::integral_constant<T, indices>{}...);

> }

> }

>

> The idea of having arguments encoded as std::integral_constant allows for

> using them not only as constexpr but also as template arguments.

>

> This simple helper function could allow us to write, for instance:

>

> /// performs the addition of two arrays of arithmetic types

> template<typename T, std::size_t N>

> auto operator +(const std::array<T, N>& lhs, const std::array<T, N>& rhs)

> -> std::enable_if_t<std::is_arithmetic_v<T>, std::array<T, N>>

> {

> return std::apply([&](auto... indices) { return std::array<T, N>{

> (std::get<indices>(lhs) + std::get<indices>(rhs))... }; },

> std::make_index_sequence<N>{});

> }

>

> int main(int argc, char** argv)

> {

> auto result = std::array{1, 2, 3} + std::array{5, 4, 3};

> apply([&](auto... indices) { (std::cout << ... << result[indices]); },

> std::make_index_sequence<3>{});

> }

>

> Even the current std::apply function for tuples could be rewriten on top

> of this proposal.

>

> No language changes are required. It can be implemented on top of C++17

> and C++14.

>

> Waiting for your feedback,

>

> Jordi

> --

> Std-Proposals mailing list

> Std-Proposals_at_[hidden]

> http://lists.isocpp.org/mailman/listinfo.cgi/std-proposals

>

Received on 2019-07-15 07:29:18