Under what circumstances is cPP a [n] a right?

refer to https://en.cppreference.com/w. under this line:

xvalue
a [n], the built-in subscript expression, where one operand is an array rvalue;

so what is array rvalue ?

refer to https://en.cppreference.com/w. to say

for expr1 [expr2]
When applied to an array, the subscript expression is an lvalue if the array is an lvalue, and an xvalue if it isn"t (since CPP11).

when is the array not a left value?

refer to the following code

struct S
{
    int iarr[10];
    int i;
    std::string sarr[10];
    std::string s;
};

S get() { return S{}; }

template<class T>
void foo(T&& v) {}

int main()
{
    foo(get().iarr[0]);//int&
    foo(get().i);      //int&&
    foo(get().sarr[0]);//std::string&
    foo(get().s);      //std::string&&
    return 0;
}

according to cppreference:

  • get () returns prvalue
  • get (). M should be xvalue
  • get (). M [n] is it xvalue ?
CPP
Mar.21,2022

simple, (int [3]) {1je 2je 3} at this time this is an array of right values. The right value returned by subscript access is the right value (xvalue), but the value returned by offset indirect addressing is always left value (the above is correct under gcc and clang), and the other way is using arryTY = int [3]; arryTY {1 Jing 2 Jing 3}


-sharpinclude <iostream>
-sharpinclude <type_traits>
-sharpinclude <typeinfo>
using namespace std;


struct S
{
    int iarr[10];
    int i;
    std::string sarr[10];
    std::string s;
};

S get() { return S{}; }

std::string sarr[10];

template<class T>
void foo(T&& v) {}
/*
decltype

a)  expression  decltype  T&& ;
b)  expression  decltype  T& ;
c)  expression  decltype  T 
 expression 

(CPP17 )
 expression  (CPP20 )

(CPP17 )
: decltype(f(g()))  g()  f() 

*/
int main()
{
    cout<<is_rvalue_reference_v <decltype(get().iarr[0])><<endl;//true ->xvalue
    cout<<is_rvalue_reference_v <decltype(get().i)><<endl;
    cout<<is_rvalue_reference_v <decltype(get().sarr[0])><<endl;//true ->xvalue
    cout<<is_rvalue_reference_v <decltype(get().s)><<endl;
    cout<<is_rvalue_reference_v <decltype(get())><<endl;
    cout<<is_rvalue_reference_v <decltype(get().iarr)><<endl;
    cout<<is_rvalue_reference_v <decltype(get().sarr)><<endl;
cout<<endl;
    cout<<is_lvalue_reference_v <decltype(get().iarr[0])><<endl;
    cout<<is_lvalue_reference_v <decltype(get().i)><<endl;
    cout<<is_lvalue_reference_v <decltype(get().sarr[0])><<endl;
    cout<<is_lvalue_reference_v <decltype(get().s)><<endl;
    cout<<is_lvalue_reference_v <decltype(get())><<endl;
    cout<<is_lvalue_reference_v <decltype(get().iarr)><<endl;
    cout<<is_lvalue_reference_v <decltype(get().sarr)><<endl;


     
    return 0;
}
Menu