Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why auto is deduced differently?

int main(){
    int x{};
    auto x2 = x;
    auto x3{x};

    static_assert(is_same<int, decltype(x)>::value, "decltype(x) is the same as int");
    static_assert(is_same<int, decltype(x2)>::value, "decltype(x2) is the same as int");
    static_assert(is_same<int, decltype(x3)>::value, "decltype(x3) is the same as int"); // Error here.
}

This codes does not compile with gcc 4.8.0. I don't even guess the type of decltype(x3). What is it? And why the behavior is different?

like image 792
Sungmin Avatar asked May 22 '13 13:05

Sungmin


2 Answers

#include <initializer_list>
#include <type_traits>

using namespace std;

int main(){
    int x{};
    auto x2 = x;
    auto x3{x};

    static_assert(is_same<int, decltype(x)>::value, "decltype(x) is the same as int");
    static_assert(is_same<int, decltype(x2)>::value, "decltype(x2) is the same as int");
    static_assert(is_same<std::initializer_list<int>, decltype(x3)>::value, "decltype(x3) is the same as int");
}

This will compile. x3 is deduced to be a std::initializer_list<int> due to:

Let T be the type that has been determined for a variable identifier d. Obtain P from T [...] if the initializer is a braced-init-list (8.5.4), with std::initializer_list<U>.

like image 125
Joseph Mansfield Avatar answered Nov 12 '22 00:11

Joseph Mansfield


So x3 is actually an std::initializer_list<int>, one way for you to have figured this out would be as follows:

std::cout << typeid(x3).name() << std::endl ;

for me I had the following output:

St16initializer_listIiE

Putting this through c++filt:

c++filt -t St16initializer_listIiE

Gives me:

std::initializer_list<int>
like image 26
Shafik Yaghmour Avatar answered Nov 11 '22 23:11

Shafik Yaghmour