C ++级联类型转换
级联类型转换时,如何让类型转换工作?
下面的代码应该很简单,但是从TypeB到int的转换需要编译器自动推导出两种类型的转换。 但事实并非如此。
我不能简单地实现运算符int()const {return val; } TypeB类,因为这应该是一个模板类我不知道要转换为哪种类型。
class TypeA {
public:
TypeA( int a ) : val( a ) {}
operator int () const { return val; }
private:
int val;
};
class TypeB {
public:
TypeB( TypeA a ) : val( a ) {}
operator TypeA () const { return val; }
// operator int() const { return val; } // Explicit conversion to int which I can not know.
private:
TypeA val;
};
void main() {
TypeA a = 9;
TypeB b = a;
int int_a = a;
TypeA a2 = b;
int int_b = b; // Compilation error:
// No suitable conversion function from 'TypeB' to 'int' exists
}
问候
所以你想让TypeB<T>
使用用户定义的T
转换?
创建一个模板operator U
,它使用SFINAE来检查T
的转换运算符,并在U
是类型T
有一个operator U
for接受。
一个不够简单的方法是std::is_convertible
- T::operator U
地址可能更好。
这需要C ++ 11功能才能合理完成,因为您需要在默认的模板参数中使用enable_if
。
这是一个粗略的实现:我没有介绍具有构造函数的源类型的目标类型。
#include <utility>
#include <type_traits>
#include <iostream>
struct A {
operator int() { return 7; }
};
template<typename T>
struct unevaluated: std::true_type {};
template<typename T, typename U, typename=void>
struct has_user_defined_conversion:std::false_type {};
template<typename T, typename U>
struct has_user_defined_conversion<T, U,
typename std::enable_if< unevaluated<
decltype(
&T::operator U
)
>::value >::type
>: std::true_type {};
template<typename T>
struct fake {
T t;
template<typename U,
typename=typename std::enable_if<has_user_defined_conversion<T,U>::value>::type
>
operator U() { return t; }
};
int main() {
int x = fake<A>();
std::cout << x << "n";
}
在任何隐式转换序列中,您最多只允许一个隐式的用户定义转换。
你可以说int int_b = static_cast<TypeA>(b);
但是,要将UDC的数量降到1个。
上一篇: C++ Cascading type conversion
下一篇: CRTP: Compiler dependent issue with Expression Template