How to construct a tuple with four elements from two pairs with matching data types in C++?
Asked Answered
K

1

6

I have a function f(), that returns a std::pair<A, B> with some types A and B. And I have another function g(), that calls f() twice and returns a std::tuple<A, B, A, B>. Is there a way to construct the return tuple directly from both calls to f()? So I would like to shortcut the last three lines of my current code:

std::tuple<A, B, A, B>
g(type1 arg1, type2 arg2, ...) {
    // perform some preprocessing
    auto pair1 = f(...);
    auto pair2 = f(...);
    return { pair1.first, pair1.second, pair2.first, pair2.second }
}

into a one liner (instead of three). It would be nice, if that solution also worked with tuples of arbitrary length, especially in a template situation.

For example, in current Python3, the solution would be return (*f(...), *f(...)). Is there a similiar list/tuple unwrap operator in C++ as there is in Python?

Koine answered 17/8, 2021 at 17:59 Comment(0)
P
7

Yes, there is std::tuple_cat. Even though cppreference says that...

The behavior is undefined if any type in [arguments] is not a specialization of std::tuple. However, an implementation may choose to support types (such as std::array and std::pair) that follow the tuple-like protocol.

I've tested it and all major standard library implementations (libstdc++, libc++, and MSVC's library) do support it.

Example:

#include <tuple>

struct A {};
struct B {};

std::pair<A, B> foo() {return {};}

std::tuple<A, B, A, B> bar()
{
    return std::tuple_cat(foo(), foo());
}
Pewter answered 17/8, 2021 at 18:2 Comment(3)
the relevant note: eel.is/c++draft/tuple.creation#12Kemerovo
and I was curious, so I looked up documentation of libstdc++, it requires __is_tuple_like<_Tpls>, but thats about as far as I was willing to dig ;) gcc.gnu.org/onlinedocs/gcc-9.2.0/libstdc++/api/…Kemerovo
@463035818_is_not_a_number I guess those are the standard tuple requirements, similar to the ones used for structured bindings and the like.Pewter

© 2022 - 2024 — McMap. All rights reserved.