Приоритет оператора в условном операторе - PullRequest
3 голосов
/ 07 мая 2020

Итак, я недавно экспериментировал с некоторыми шаблонами, и это был код, на который я наткнулся:

template <typename T>
int someFunction(T someParameter)
{
    return  std::is_same<T, bool>::value ? 1 : 0 +
            std::is_same<T, char>::value ? 2 : 0 +
            std::is_same<T, int>::value  ? 3 : 0;
}

Так что, по сути, это набор условных операторов, которые возвращают значение, если оно истинно, или вообще ничего если ложь. И если вы сложите их вместе, вы можете определить, какой тип данных является аргументом.

Однако я кое-что понял. Имеют ли значение скобки? Я попытался заключить код в скобки, например:

template <typename T>
int someFunction(T someParameter)
{
    return  (std::is_same<T, bool>::value ? 1 : 0) +
            (std::is_same<T, char>::value ? 2 : 0) +
            (std::is_same<T, int>::value  ? 3 : 0);
}

Но результат остался прежним. Итак, я подумал, может быть, компилятор увидит что-то вроде этого:

template <typename T>
int someFunction(T someParameter)
{
    return  std::is_same<T, bool>::value ? 1 : (0 +
            std::is_same<T, char>::value ? 2 : (0 +
            std::is_same<T, int>::value  ? 3 : 0));
}

Таким образом, он в некотором смысле сначала оценивает последний условный оператор и работает в обратном направлении. Но я все еще не могу осмыслить эту штуку, и я не уверен, правильно ли я это понимаю.

Может ли кто-нибудь сказать мне, какой здесь приоритет оператора и как он выполняется? Спасибо.

1 Ответ

3 голосов
/ 07 мая 2020

Да, operator+ имеет более высокий приоритет , чем оператор условия, поэтому

return  std::is_same<T, bool>::value ? 1 : 0 +
        std::is_same<T, char>::value ? 2 : 0 +
        std::is_same<T, int>::value  ? 3 : 0;

интерпретируется как

return  std::is_same<T, bool>::value ? 1 : 
          ( 0 + std::is_same<T, char>::value ) ? 2 : 
            ( 0 + std::is_same<T, int>::value ) ? 3 : 0;

и будет более понятным

return  std::is_same<T, bool>::value ? 1 : 
          ( ( 0 + std::is_same<T, char>::value ) ? 2 : 
            ( ( 0 + std::is_same<T, int>::value ) ? 3 : 0 ) );

Результатом будет 1 для bool, 2 для char, 3 для int.

Примерно 0 + std::is_same<T, ...>::value, std::is_same<T, ...>::value - это bool, при использовании в качестве операнда operator+ он будет неявно преобразован в int как 1 для true, 0 для false. После этого результат сложения используется как условие и преобразуется в bool обратно как false для 0 и true для ненулевого значения.

...