Most of the cases where this conversion happens are covered by [expr]#8:
Whenever a glvalue expression appears as an operand of an operator that expects a prvalue for that operand, the lvalue-to-rvalue (4.1), array-to-pointer (4.2), or function-to-pointer (4.3) standard conversions are applied to convert the expression to a prvalue.
All of the operators which can take arr
expect a prvalue (or otherwise explicitly request this conversion), except for:
- unary
&
sizeof
++
--
alignof
typeid
(Note: this list might not be exhaustive, I will update it if someone points out other cases!)
Now, There are various possible cases where we can use arr
and it is not the operand of any operator. Some of those cases perform the conversion and some don't. The ones that do perform the conversion are:
- using
arr
as a function argument but not matching a prototype parameter
- some cases of template type deduction
- deducing the return type of a lambda
Notably, the conversion is not performed by binding arr
to a reference (this is what happens in the range-based for-loop). This is covered by [dcl.init.ref]#5. In the line T &ref = arr;
, the =
is not the assignment operator; it's part of the syntax for declarations.
与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…