c++ - 为什么这段代码用 gcc 编译而不用 clang

标签 c++ c++11 g++ clang++

此代码与 gcc/g++ 和 msvc 完美结合,但不适用于 clang。 一直报找不到Log的匹配函数,这是怎么回事?

#include <iostream>

template <typename Function, typename... Args>
auto Call(Function func, Args&&... args) -> typename std::result_of<Function&(Args&&...)>::type
{
    return func(std::forward<Args>(args)...);
}

template <typename T, typename... Args>
T (*Log( T (*FuncPtr)(Args...) ))(Args...)
{
    return FuncPtr;
}

int main()
{
    auto r = Log(Call<int(int), int>)([](int x){
        return x*10;
    }, 10);
    std::cerr << r << std::endl;
}

错误:

> error: no matching function for call to 'Log'
>     auto r = Log(Call<int(int), int>)([](int x){
>              ^~~ test7.cpp:15:5: note: candidate template ignored: couldn't infer template argument 'T' T (*Log( T (*FuncPtr)(Args...)
> ))(Args...)
>     ^ 1 error generated.

最佳答案

我认为此代码不正确。在这种情况下,Log 的函数参数不能用于模板参数推导,因为该参数是非推导上下文。

从标准中的[temp.deduct.type]中,p5列出了非推导的上下文,p5.5说:

A function parameter for which argument deduction cannot be done because the associated function argument is a function, or a set of overloaded functions (13.4), and one or more of the following apply:

p5.5.3 说:

the set of functions supplied as an argument contains one or more function templates.

我的解释是你有一个函数参数,它的函数参数是一个(指向)函数,而该函数是一个函数模板。

可以说,因为这不是一个重载集,所以将来可能会允许这样做,但我认为标准并不保证这种技术会起作用。

关于c++ - 为什么这段代码用 gcc 编译而不用 clang,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37493026/

相关文章:

python - 在多线程中调用 Py_Initialize()

c++ - 关于如何在基于动态数组的结构中存储键值对的想法

c++ - 无法将 GLFW 库与其在 Ubuntu 18.04 上的头文件链接起来

c++ - Scons:如何在编译前使用不产生任何输出文件的命令检查文件?

C++ 意外的整数提升

c++ - 为什么可以接受对不同类型变量的常量引用?

c++ - 在没有声明符的情况下显式调用构造函数

c++ - 更快的 WinSock sendto()

c++ - 没有 cruft 的 C++ "in"运算符?

c++ - 局部静态变量初始化是线程安全的