c++ - 如何检测函数是否存在?

标签 c++ c++11 templates metaprogramming template-meta-programming

我正在尝试检测我的函数的特定重载是否可调用。我以为我可以做类似于 this answer 的事情,但我认为问题在于函数签名 template<typename From, typename To> convert(const From&)定义明确,但实例化不是。

#include <iostream>
#include <string>

template<typename From, typename To>
To convert(const From& from)
{
    // I have a lot of additional template specializations for this function
    return from; 
}

template<typename From, typename To>
struct IsConvertible
{
    template<typename = decltype(convert<From, To>(From()))>
    static std::true_type test(int);
    template<typename T>
    static std::false_type test(...);

    static bool const value = decltype(test(0))::value;
};

int main()
{
    std::cout << "IsConvertible=" << IsConvertible<int, float>::value << std::endl;
    // Returns 1 as expected

    std::cout << "IsConvertible=" << IsConvertible<int, std::string>::value << std::endl;
    // Returns 1, expected 0. The issue seems to be that decltype(convert<From, To>(From()))
    // is somehow ok, although convert<int, std::string>(1) definitly isn't
}

我想使用 IsConvertible一些额外的元编程。 是否可以检测 template<typename From, typename To> To convert(const From&)函数实际上是可调用的?`

最佳答案

声明

template<typename From, typename To> To convert(const From& from);

你的特点

template<typename From, typename To>
struct IsConvertible

将始终检测是否存在 convert 函数。

修复它的一种方法是重载和/或 SFINAE:

template <typename> struct Tag{};

int convertImpl(tag<int>, const std::string& from);
float convertImpl(tag<float>, const std::string& from);
// overloads ...

template<typename From, typename To>
auto convert(const From& from)
-> decltype(convertImpl(tag<To>{}, from))
{
    return convertImpl(tag<To>{}, from);
}

关于c++ - 如何检测函数是否存在?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56072291/

相关文章:

c++ - 使用 Xcode 13 在 iOS 15 上编译 Cronet 时,shrink_to_fit() 的 "Undefined symbols"

c++ - 模板参数 - 带有可变参数的函数指针

java - 使用 t :pagelink and context 在 Java Tapestry 中创建 anchor 链接

c++ - 带有基类的模板类

c++ - _Pass_fn : where is the constructor?

c++ - 将pointcloud2数据转换为opencv图像

c++ - Eclipse CDT (4.5.1) 打印效果很慢

c++ - 使用 std::bind 分别绑定(bind)参数和对象实例

c++ - gcc 的 boost::variant 链接器错误

c++ - 如何在 Android NDK 中使用 c++0x 线程?