Search code examples
c++autoinitializer-list

How does auto deal with multiple values in () initializer?


I know for C++11 way of initializing a vector using auto, actually an std::initializer_list is initialized instead of a vector. However, given below piece of code:

#include <iostream>
#include <vector>
using namespace std;

int main() {
    auto x = {1, 2};
    cout << typeid(x).name() << endl;
    auto z = (1, 2);
    cout << z << ", type: " << typeid(z).name() << endl;
    return 0;
}

I don't understand:

  1. Why the type of x returned is St16initializer_listIiE and the type of 'z' returned is 'i', using gcc-10 compiler. Shouldn't we just return std::initializer_list and 'int'?
  2. There is a warning on z: warning: left operand of comma operator has no effect [-Wunused-value]. Then the 2nd half of result is: 2, type: i. How does c++11 interpret ()-initialized type? Why is only the last element passed into z and thus z is still of type int?

Solution

  • Why the type of x returned is St16initializer_listIiE and the type of 'z' returned is 'i', using gcc-10 compiler. Shouldn't we just return std::initializer_list and 'int'?

    typeid() won't directly give what you would expect, it just returns the specific type identification as written down in its code. If you would like to decrypt the same, pass it via c++filt:

    c++filt -t St16initializer_listIiE
    

    It will result in what you were expecting, i.e. an:

    std::initializer_list<int>
    

    There is a warning on z: warning: left operand of comma operator has no effect [-Wunused-value]. Then the 2nd half of result is: 2, type: i. How does c++11 interpret ()-initialized type? Why is only the last element passed into z and thus z is still of type int?

    ( ) is an initializer holding an expression, or a list of expressions. If you were to assign that to auto, it would select the very last item in the expression list as its type as it would be seperated by commas till the advent of the last expression, which ideally tells auto to assign its type to the last one.

    For Example:

    auto x = (1, 1.5L); 
    

    would result in a long.

    auto x = (1, 1.5f);
    

    would result in a float.

    auto x = (1, "string");
    

    would result in a const char pointer.

    It entirely neglects the first value within the ( ) initializer, which is an int.