C ++模板转换函数

时间:2016-09-18 15:01:44

标签: c++ templates

假设以下类型:

enum class MyEnum1 {};
enum class MyEnum2 {};
typedef struct MyStruct1 {};
typedef struct MyStruct2 {};

以及以下(愚蠢的)转换:

MyEnum1 convert_to_MyEnum2(MyEnum2 e) { return MyEnum1(); }
MyEnum2 convert_to_MyEnum1(MyEnum1 e) { return MyEnum2(); }
MyStruct1 convert_to_MyStruct1(MyStruct2 s) { return MyStruct1(); }
MyStruct2 convert_to_MyStruct2(MyStruct1 s) { return MyStruct2(); }

我希望有一个转换函数,它只需一种类型并将其转换为另一种类型。

现在,由于函数总是接受一个不同的类型,并且不仅仅是返回类型不同,我显然可以将所有convert_to_*更改为convert并使所有可能性重载此函数我有。

但是,我不喜欢让用户写下类似的东西:

auto e1 = convert(e2);
Foo(convert(e1));

我希望代码可读,所以我想要有类似的东西:

//make all "convert" overloads private and only expose this function
template<typename To, typename From>
To convert_to(From from)
{
    return convert(from); 
}

这样代码将是:

auto e1 = convert_to<MyEnum1>(e2);
Foo(convert_to<MyEnum2>(e1));

1-是否可以避免convert重载但仍然使用某种单入口点\单个函数名来实现我想要的? (即找到现有convert_to_x)的一些用法

2-我明白这与代码审查有关,但这个问题的推荐方法(如果存在)是什么?

1 个答案:

答案 0 :(得分:1)

是的,可以使用template specialization实现涵盖具有单个名称的多种类型的转换功能。

enum class MyEnum1 {};
enum class MyEnum2 {};
struct MyStruct1 {};
struct MyStruct2 {};

// Unimplemented general fall-back case.
// Note: there are more civilized ways to issue a compilation error...
template<typename To, typename From>
To convert_to(From from) { return To::unimplemented_conversion; }

template<> MyEnum1 convert_to(MyEnum2 from) { return MyEnum1(); }
template<> MyEnum2 convert_to(MyEnum1 from) { return MyEnum2(); }
template<> MyStruct1 convert_to(MyStruct2 from) { return MyStruct1(); }
template<> MyStruct2 convert_to(MyStruct1 from) { return MyStruct2(); }

int main()
{
    MyEnum2 e2 = convert_to<MyEnum2>(MyEnum1());
    MyEnum1 e1 = convert_to<MyEnum1>(e2);
    // MyStruct1 s1 = convert_to<MyStruct1>(e2);  unimplemented conversion
    return 0;
}