This is an unofficial snapshot of the ISO/IEC JTC1 SC22 WG21 Core Issues List revision 115d. See http://www.open-std.org/jtc1/sc22/wg21/ for the official list.
2024-10-26
[Accepted as a DR at the November, 2022 meeting.]
13.7.4 [temp.variadic] paragraph 10 expands a fold-expression (including its enclosing parentheses) to an unparenthesized expression. If interpreted literally, this could result in reassociation and misinterpretation of the expression. For example, given:
template<int ...N> int k = 2 * (... + N);
... k<1, 2, 3> is specified as expanding to int k<1, 2, 3> = 2 * 1 + (2 + 3); resulting in a value of 7 rather than the intended value of 12.
Further, there is implementation divergence for the following example:
#include <type_traits> template<class ...TT> void f(TT ...tt) { static_assert(std::is_same_v<decltype((tt, ...)), int&>); } template void f(int /*,int*/);
gcc and MSVC apply the general expression interpretation
of decltype
, whereas clang and icc apply
the identifier special case.
Proposed resolution (approved by CWG 2022-08-26):
Change in 13.7.4 [temp.variadic] paragraph 10 as follows:The instantiation of a fold-expression (7.5.7 [expr.prim.fold]) produces:...
- ( ((E1 op E2 ) op . . . ) op EN ) for a unary left fold,
- ( E1 op (. . . op (EN-1 op EN )) ) for a unary right fold,
- ( (((E op E1 ) op E2 ) op . . . ) op EN ) for a binary left fold, and
- ( E1 op (. . . op (EN-1 op (EN op E))) ) for a binary right fold.