SFINAE 构造函数 [英] SFINAE Constructors

查看:46
本文介绍了SFINAE 构造函数的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我一直喜欢这样的函数式 SFINAE 语法,似乎通常运行良好!

I have been liking SFINAE syntax like this for functions, seems to generally work well!

template <class Integer, class = typename std::enable_if<std::is_integral<Integer>::value>::type>
T(Integer n) {
    // ...
}

但是当我也想在同一个班级中这样做时遇到了问题......

But am running into an issue when I want to do this as well in the same class...

template <class Float, class = typename std::enable_if<std::is_floating_point<Float>::value>::type>
T(Float n) {
    // ...
}

出现这样的错误:

./../T.h:286:2: error: constructor cannot be redeclared
        T(Float n) {
        ^
./../T.h:281:2: note: previous definition is here
        T(Integer n) {
        ^
1 error generated.

这些构造函数不应该只存在于适当的类型中,而不应该同时存在吗?为什么它们会冲突?

Shouldn't these constructors only exist for the appropriate types and never at the same time? Why do they conflict?

我这里有点厚吗?

另一方面这确实有效(但我不太喜欢这种语法):

This on the other hand does work (but I don't like the syntax as much):

template <class Integer>
T(Integer n, typename std::enable_if<std::is_integral<Integer>::value>::type* = nullptr) {
}

template <class Float>
T(Float n, typename std::enable_if<std::is_floating_point<Float>::value>::type* = nullptr) {
}

推荐答案

改用非类型模板参数:

template <class Integer,
    std::enable_if_t<std::is_integral<Integer>::value, int> = 0>
T(Integer n) {
    // ...
}

template <class Float,
    std::enable_if_t<std::is_floating_point<Float>::value, int> = 0>
T(Float n) {
    // ...
}

这是可行的,因为编译器必须先替换第一个模板参数,然后才能确定值参数的类型.

This works because the compiler has to substitute the first template parameter before it can determine the type of the value parameter.

这篇关于SFINAE 构造函数的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆