Почему сужающее преобразование, используемое с инициализатором с разделителями в виде фигурных скобок, не вызывает ошибку?
Я узнал об инициализаторе, разделенном фигурными скобками, в языке программирования C ++, 4-е изд. > Глава 2: Тур по C ++: Основы.
Я цитирую из книги ниже.
Форма = традиционна и восходит к C, но в случае сомнений используйте общую форму {} -list (§6.3.5.2). Если ничего другого, это спасает вас от конверсий, которые теряют информацию (сужение конверсий; §10.5):
int i1 = 7.2; // i1 becomes 7
int i2 {7.2}; // error : floating-point to integer conversion
int i3 = {7.2}; // error : floating-point to integer conversion (the = is redundant)
Однако я не могу воспроизвести эти результаты.
У меня есть следующий код.
#include <iostream>
int main()
{
int i1 = 7.2;
int i2 {7.2};
int i3 = {7.2};
std::cout << i1 << "\n";
std::cout << i2 << "\n";
std::cout << i3 << "\n";
}
Когда я компилирую и запускаю его, я не получаю никакой ошибки. Я получаю предупреждение оstd=c++11
но без ошибок.
$ g++ init.cpp
init.cpp: In function ‘int main()’:
init.cpp:6:12: warning: extended initializer lists only available with -std=c++11 or -std=gnu++11
int i2 {7.2};
^
$ ./a.out
7
7
7
Кроме того, предупреждение относится только ко второму назначению, но нет предупреждения для третьего назначения. Это, кажется, указывает на то, что=
на самом деле не является избыточным, как упомянуто в книге. Если=
были бы избыточными, либо второе и третье назначения вызвали бы предупреждения, либо оба не дали бы предупреждения. Затем я собираю их с-std=c++11
флаг.
$ g++ -std=c++11 init.cpp
init.cpp: In function ‘int main()’:
init.cpp:6:16: warning: narrowing conversion of ‘7.2000000000000002e+0’ from ‘double’ to ‘int’ inside { } [-Wnarrowing]
int i2 {7.2};
^
init.cpp:7:18: warning: narrowing conversion of ‘7.2000000000000002e+0’ from ‘double’ to ‘int’ inside { } [-Wnarrowing]
int i3 = {7.2};
^
$ ./a.out
7
7
7
Все еще нет ошибки. Только предупреждения. Хотя в этом случае второе и третье назначения ведут себя одинаково по отношению к генерации предупреждений.
Итак, мой вопрос: хотя в книге упоминается, что второе и третье присваивания являются ошибками, почему этот код не может скомпилироваться?