Development Tip

auto x {3}가 initializer_list를 추론하는 이유는 무엇입니까?

yourdevel 2020. 12. 31. 23:01
반응형

auto x {3}가 initializer_list를 추론하는 이유는 무엇입니까?


저는 autoC ++ 11을 좋아 합니다. 훌륭합니다. 그러나 그것은 항상 내 신경을 쓰러 뜨리는 한 가지 불일치가 있습니다.

int i = 3;       // i is an int with value 3
int i = int{3};  // i is an int with value 3
int i(3);        // i is an int with value 3 (possibly narrowing, not in this case)
int i{3};        // i is an int with value 3

auto i = 3;      // i is an int with value 3
auto i = int{3}; // i is an int with value 3
auto i(3);       // i is an int with value 3
auto i{3};       // wtf, i is a std::initializer_list<int>?!

이 이상한 동작은 초보자에게는 혼란스럽고 숙련 된 사용자에게는 성가신 일입니다. C ++에는있는 그대로 염두에 두어야 할 불일치와 코너 케이스가 충분합니다. 이 경우에 표준위원회가 새로운 것을 도입하기로 결정한 이유를 설명 할 수 있습니까?

유형의 변수를 선언하는 std::initializer_list것이 유용하거나 자주 수행되는 일 이라면 이해할 수 있었지만 제 경험상 거의 고의적이지 않았습니다. 드물게 원하는 경우

std::initializer_list<int> l{3};
auto l = std::initializer_list<int>{3};
auto l = {3}; // No need to specify the type

잘 작동합니다. 그래서 특별한 경우의 이유는 auto x{i}무엇입니까?


긴 이야기를 짧게 만들려면 :

  • 중괄호 이니셜 라이저 표현식 {}에는 자체적으로 유형이 없습니다.
  • auto 유형 정보를 추론해야합니다.
  • int{3}명백하게 "는 생성 수단 int따라서 그 종류가 그냥, 이니셜리스트로부터 취해진 값을 VAR" int(있는 넓은 맥락에서 사용될 수있는 int i = int{3}작동 및 auto i = int{3}우측 분명 형이기 때문에, 형을 추론 할 수 int)
  • {3}그 자체가 어떤 유형이 없습니다에 의해 (이 할 수없는int이이 아니기 때문에, 하지만, 초기화 목록 때문에) auto것하지 작업 -위원회가 고려하기 때문에,하지만 auto이 경우에해야 여전히 일을, 그들이 "최고"유형 결정 for (예, 정의에 따라 유형이 없음) 이니셜 라이저 목록은 std::initializer_list이미 짐작했듯이 ... 입니다.

그러나, 당신이 지적했듯이, 이것은 전체적인 동작을 auto의미 적으로 일관성 이 없게 만들었습니다 . 그래서 N3681 , N3912N3922 변경 제안 이위원회에 제출되었습니다. 전 제안은 때문에이 문제에 어떤위원회 합의에 FI3으로 거부 http://isocpp.org/files/papers/n3852.html#FI3 , 현재 ( N3922 있어) 채택 약을 2015 년 1 분기 ;

tl; dr 당신은 최첨단 C ++ 지원 2 를 가진 표준 준수 컴파일러 1이미 새롭고 더 건전한 의미를 가지고 있거나 곧 그것을 가질 것이라고 가정 할 수 있습니다.

표준화위원회는 C ++ 17 초안에 N3922를 채택하여 문제를 인정했습니다.

— 그래서 그것은

auto x1 = { 1, 2 }; // decltype(x1) is std::initializer_list<int>
auto x2 = { 1, 2.0 }; // error: cannot deduce element type
auto x3{ 1, 2 }; // error: not a single element
auto x4 = { 3 }; // decltype(x4) is std::initializer_list<int>
auto x5{ 3 }; // decltype(x5) is int

지금, 좋든 나쁘 든.

추가 읽기 :

http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2013/n3681.html

http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n3912.html

http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n3922.html

http://scottmeyers.blogspot.com/2014/03/if-braced-initializers-have-no-type-why.html

http://herbsutter.com/2014/11/24/updates-to-my-trip-report/


1 GCC 5.1 (이상) 은 C ++ 11 / C ++ 14 모드에서도 분명히 N3922를 사용합니다.

2 Clang 3.8 (주의 사항 포함)

이것은 자동에서 유형 추론을 허용하는 모든 언어 버전에 적용되는 이전 버전과 호환되지 않는 변경입니다 (C ++위원회의 요청에 따라).

참조 URL : https://stackoverflow.com/questions/25612262/why-does-auto-x3-deduce-an-initializer-list

반응형