template <class Rhs, class Ret=dont_care>
struct has_unary_minus : public true_type-or-false_type
{};
Наследники:Если (i)<rhs
>типа<Rhs
>можно использовать в выражении<-rhs
>, и (ii)<Ret=dont_care
>или результат выражения<-rhs
>конвертируем в<Ret
>, то наследуется отtrue_type, в противном случае наследуется отfalse_type.
По умолчанию поведение<Ret=dont_care
>не проверяется на возвратное значение префикса<operator-
>. Если<Ret
>отличается от типа по умолчанию<dont_care
>, то значение возврата проверяется на конвертируемость в<Ret
>. Конвертируемое к<Ret
>означает, что возвращаемое значение оператора может быть использовано в качестве аргумента для функции, ожидающей<Ret
>:
void f(Ret);
Rhs rhs;
f(-rhs);
Если<Ret=void
>, то тип возврата проверяется точно<void
>.
Заголовок:<#include
<boost/type_traits/has_unary_minus.hpp>
>или<#include<boost/type_traits/has_operator.hpp>
>или<#include<boost/type_traits.hpp>
>
Совместимость компилятора:Требуется работа SFINAE (т.е. BOOST_NO_SFINAE не установлен). Этого не поддерживает лишь меньшинство довольно старых компиляторов.
Примеры:
<has_unary_minus<Rhs,Ret>::value_type
>является типом<bool
>.
<has_unary_minus<Rhs,Ret>::value
>— интегральное постоянное выражение<bool
>.
<has_unary_minus<int>::value
>— интегральное постоянное выражение<bool
>, оценивающее до<true
>.
<has_unary_minus<long>
>наследуется от<true_type
>.
<has_unary_minus<int,int>
>наследуется от<true_type
>.
<has_unary_minus<int,long>
>наследуется от<true_type
>.
<has_unary_minus<double,double>
>наследуется от<true_type
>.
<has_unary_minus<double,int>
>наследуется от<true_type
>.
<has_unary_minus<constint>
>наследуется от<true_type
>.
<has_unary_minus<int,std::string>
>наследуется от<false_type
>.
См. также:Типы операторов
Известные вопросы:
- Эта черта не может определить, является ли префикс<
operator-
>общедоступным или нет: если<operator-
>определен как частный член<Rhs
>, то инстанцирование<has_unary_minus<Rhs>
>приведет к ошибке компилятора. По этой причине<has_unary_minus
>не может использоваться для определения того, имеет ли тип публичный<operator-
>или нет.<structA{private:voidoperator-();};
boost::has_unary_minus<A>::value;
>
- Существует проблема, если оператор существует только для типа<
A
>и<B
>является конвертируемым в<A
>. В этом случае компилятор сообщит о двусмысленной перегрузке.<structA{};
voidoperator-(constA&);
structB{operatorA();};
boost::has_unary_minus<A>::value;
boost::has_unary_minus<B>::value;
>
- Существует проблема при применении этой черты к классам шаблонов. Если<
operator-
>определено, но не связывается для данного типа шаблона, он все еще обнаруживается чертой, которая возвращается<true
>вместо<false
>. Пример:<#include<boost/type_traits/has_unary_minus.hpp>
#include<iostream>
template<classT>
structcontains{Tdata;};
template<classT>
booloperator-(constcontains<T>&rhs){
returnf(rhs.data);
}
classbad{};
classgood{};
boolf(constgood&){}
intmain(){
std::cout<<std::boolalpha;
std::cout<<boost::has_unary_minus<contains<good>>::value<<'\n';
contains<good>g;
-g;
std::cout<<boost::has_unary_minus<contains<bad>>::value<<'\n';
contains<bad>b;
-b;
return0;
}
>
- <
volatile
>квалификатор не обрабатывается должным образом и приведет к неопределенному поведению