C++ Logo

std-proposals

Advanced search

Re: [std-proposals] Fold expression contains 'if constexpr'

From: Lénárd Szolnoki <cpp_at_[hidden]>
Date: Sun, 04 Dec 2022 23:22:55 +0000
Hi,

On 4 December 2022 22:40:25 GMT, Frederick Virchanza Gotham via Std-Proposals <std-proposals_at_[hidden]> wrote:
>I wanted to write the following function containing a fold expression:
>
>template<typename... Types>
>auto Func(Types... a)
>{
> using std::get;
> decltype(pointers) &p = pointers;
>
> (if constexpr(requires{ get<Types>(p)->Method(a...); }) return
>get<Types>(p)->Method(a...), ...);
>}
>
>but since we can't have 'if constexpr' inside a fold expression, I
>instead had to write:
>
>template<typename... Types>
>auto Func(Types... a)
>{
>using std::get;
>
>decltype(pointers) &p = pointers;
>
> if constexpr(requires{get< 0>(p)->Method(a...); })return get<
>0>(p)->Method(a...);
>else if constexpr(requires{get< 1>(p)->Method(a...); })return get<
>1>(p)->Method(a...);
>else if constexpr(requires{get< 2>(p)->Method(a...); })return get<
>2>(p)->Method(a...);
>else if constexpr(requires{get< 3>(p)->Method(a...); })return get<
>3>(p)->Method(a...);
>else if constexpr(requires{get< 4>(p)->Method(a...); })return get<
>4>(p)->Method(a...);
>else if constexpr(requires{get< 5>(p)->Method(a...); })return get<
>5>(p)->Method(a...);
>else if constexpr(requires{get< 6>(p)->Method(a...); })return get<
>6>(p)->Method(a...);
>else if constexpr(requires{get< 7>(p)->Method(a...); })return get<
>7>(p)->Method(a...);
>else if constexpr(requires{get< 8>(p)->Method(a...); })return get<
>8>(p)->Method(a...);
>else if constexpr(requires{get< 9>(p)->Method(a...); })return get<
>9>(p)->Method(a...);
>else if constexpr(requires{get<10>(p)->Method(a...); })return
>get<10>(p)->Method(a...);
>else if constexpr(requires{get<11>(p)->Method(a...); })return
>get<11>(p)->Method(a...);
>else if constexpr(requires{get<12>(p)->Method(a...); })return
>get<12>(p)->Method(a...);
>else if constexpr(requires{get<13>(p)->Method(a...); })return
>get<13>(p)->Method(a...);
>else if constexpr(requires{get<14>(p)->Method(a...); })return
>get<14>(p)->Method(a...);
>else if constexpr(requires{get<15>(p)->Method(a...); })return
>get<15>(p)->Method(a...);
>}
>
>Is there some how some way that we can allow 'if constexpr' inside a
>fold expression? I know that we can have a fold expression containing
>a lambda (and that the lambda can contain 'if constexpr'), but in this
>example we need 'if constexpr' by itself.

Note that apart from an if of if constexpr statement, you can't have a return statement in a fold expression either. There is absolutely no way to short-circuit a fold expression, unless it's fold over && or ||, and even then, it needs to be the built-in operator. This limits fold expressions somewhat.

There were some proposals to introduce for loops over packs, I don't know the state of those. That would solve this issue quite elegantly.

Cheers,
Lénárd

Received on 2022-12-04 23:23:00