Кажется, я нашел кое-что, с чем расходятся Clang и GCC. Вот код:
int main() {
if constexpr (2) {}
}
Это успешно компилируется с GCC 7.4.0, но не работает с Clang 7.0.0 с этим сообщением об ошибке:
test.cpp:3:17: error: constexpr if condition evaluates to 2, which cannot be narrowed to type 'bool'
[-Wc++11-narrowing]
if constexpr (2) {}
^
1 error generated.
cppreference, похоже, не упоминает «сужение», так что это похоже на ошибку Clang, но я не совсем уверен. Если это ошибка одного из компиляторов, о ней уже сообщалось?
(!!2) будет работать, но 2 тоже должно работать.
Я только что проверил. !!2 работает с лязгом





Clang проводит диагностику по этим параграфам
[stmt.if] (emphasis mine)
2 If the if statement is of the form if constexpr, the value of the condition shall be a contextually converted constant expression of type bool; this form is called a constexpr if statement.
[expr.const]
4 A converted constant expression of type T is an expression, implicitly converted to type T, where the converted expression is a constant expression and the implicit conversion sequence contains only
- integral conversions other than narrowing conversions,
Теперь, когда дело доходит до интегральных преобразований, преобразование кboolуказан как интегральное преобразование. И это сужение в самом строгом смысле этого слова, поскольку логическое значение не может представлять все значения int. Так что диагностика не без оснований.
Но я также думаю, что вполне разумно учитывать тот факт, что преобразование в bool обычно предназначено для проверки «правдивости», поэтому его сужающий характер не должен иметь значения. Это похоже на незначительную ошибку в стандарте1, когда GCC идет по пути здравого смысла, а Clang придерживается сухой буквы закона в самом строгом смысле.
1 - And a proposal exists to change it.
Ошибка в стандарте! ржу не могу
@ Rakete1111 - беззастенчиво добавил к ответу :) Спасибо!
Мы говорим это, но это скрыто. «Контекстно преобразованное константное выражение типа bool» — это стандартный термин, исключающий сужающие преобразования.
Кланг прав.
Согласилась ли CWG с тем, что текущая формулировка стандарта является предполагаемой?
Что, если вы сделаете
if constexpr (!!2) {}?