我有一个类似的问题,就像发现的问题 here但可能我仍在做一些不同的事情,所以我还是会问。
有一些类型将使用标签结构进行标记:
template<typename Geometry=void, typename Enable = void>
struct tag
{
typedef void type;
};
以及点和三角形标签的介绍:
struct point_tag {};
struct triangle_tag {};
使用std::vector
构造点类型:
template<>
struct tag<std::vector<double>>
{
typedef point_tag type;
};
和一个三角形类型作为std::array
的别名模板:
template<typename Point>
using triangle =
typename std::enable_if
<
std::is_base_of<typename tag<Point>::type, point_tag>::value,
std::array<Point,3>
>::type;
如果作为 Point
参数传递的参数确实用 point_tag
标记,则启用该功能,
然后,我想用 triangle_tag
标记所有三角形,如下所示:
template <typename Point>
struct tag<triangle<Point>>
{
typedef triangle_tag type;
};
std::array
是别名且未合成/继承,因为组合和继承会导致 initializer list construction 出现问题。 。但是,编译失败并出现错误
g++ -std=c++1y main.cpp -o main
main.cpp:31:8: error: template parameters not deducible in partial specialization:
struct tag<triangle<Point>>
^
main.cpp:31:8: note: ‘Point’
如果我不依赖于基于标记的 Point
参数启用 triangle
,而是对所有类型执行此操作,如下所示:
template<typename Point>
using triangle =
// This works, but there is no restriction on Point to be tagged with point_tag.
std::array<Point, 3>;
然后编译就可以正常工作了。但是,三角形也是三角形,我使用 function overloading based on arbitrary properties of types减少 enable_if
失败的函数的函数模板集。我不依赖函数模板的容器接口(interface)来确定可行的模板参数,因为有时隐式接口(interface)完全相同,但操作语义不同。例如,三角形是闭合的圆形线段(涉及3条边的操作),点链是开放的线段(涉及2条边的操作)。所有操作都需要直接访问运算符,这是对模板参数的唯一要求,这会导致在没有 enable_if
限制的情况下实现函数模板实例化时出现歧义 - 所有这些都在链接的文章中介绍。
这是complete example 。
我有什么遗漏的吗?如何解决这个问题?
最佳答案
什么不使用您的 Enable
模板参数?
像这样的东西:
template <typename Point>
struct tag<
std::array<Point, 3>,
typename std::enable_if<
std::is_base_of<
typename tag<Point>::type,
point_tag
>::value
>::type
>
{
typedef triangle_tag type;
};
(好的,您重复enable_if
...)
关于c++ - 模板参数在部分特化中不可推导,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24954847/