到目前为止,这是我尝试过的:
这是我的代码:
template<typename T1>
struct Foo
{
template<typename T2>
using MyPair = std::pair<T1, T2>;
using MyPairs = std::vector<MyPair>;
Foo()
{
//if T1 is an int, then I want T2 to be a double.
//if T1 is a float, then I want T2 to be an int.
}
};
如果T2
是double
,我希望T1
是int
。如果
T2
是int
,我希望T1
是float
。我该怎么做?
最佳答案
有很多解决方法。
选项-我
简单的方法是使用 std::conditional
定义T2
的别名。其中,如果T1 == int
的T2
将为double
,所有其他类型,则T2
将为int
的别名。 (See a demo)
#include <utility>
#include <type_traits> // std::conditional, std::is_same
template<typename T1>
struct Foo /* final */
{
static_assert(std::is_same<T1, int>::value || std::is_same<T1, float>::value, "NOT A VALID TYPE T1");
using T2 = typename std::conditional<std::is_same<T1, int>::value, double, int>::type;
using MyPair = std::pair<T1, T2>;
};
如果要限制其他类型的类的实例化,请提供该类的条件实例化或 static_assert
。选项-II
您可以使用特质特化来定义
T2
类型。 (See a demo)#include <vector>
#include <utility>
// base template!
template <typename T1> struct helper_traits;
template <> // when helper_traits<`T1 == int`> then `T2 == double`
struct helper_traits<int> final { using T2 = double; };
template <> // when helper_traits<`T1 == float`> then `T2 == int`
struct helper_traits<float> final { using T2 = int; };
template<typename T1>
struct Foo /* final */
{
using T2 = typename helper_traits<T1>::T2; // will select the proper one!
using MyPair = std::pair<T1, T2>;
};
选项-III
在c++17中,可以使用
if constexpr
决定要在函数中返回哪种类型,并使用它来了解T2
的类型,如下所示:(See a demo)
#include <type_traits> // std::is_same_v
template<typename T1>
struct Foo /* final */
{
template<typename Type>
static constexpr auto typeHelper() noexcept
{
if constexpr (std::is_same_v<Type, int>)
return double{};
else if constexpr (std::is_same_v<Type, float>)
return int{};
}
using T2 = decltype(Foo<T1>::typeHelper<T1>()); // will select the proper one!
using MyPair = std::pair<T1, T2>;
};