如何为重载函数声明模板参数

How to declare the template argument for an overloaded function

我有一个相当大的项目,关于这个问题, 我可以总结一下 this structure:

void do_something()
{
    //...
}

template<typename F> void use_funct(F funct)
{
    // ...
    funct();
}

int main()
{
    // ...
    use_funct(do_something);
}

一切正常,直到有人(我)决定稍微重新格式化 最小化一些功能,重写 as this minimum reproducible example:

void do_something(const int a, const int b)
{
    //...
}

void do_something()
{
    //...
    do_something(1,2);
}

template<typename F> void use_funct(F funct)
{
    // ...
    funct();
}

int main()
{
    // ...
    use_funct(do_something);
}

现在代码无法编译 错误:没有匹配的调用函数 其中 use_funct 被实例化。

因为错误信息对我来说不是很清楚 变化很大,我浪费了相当多的钱 了解编译器的时间量 无法推断模板参数 因为 do_something 现在可以参考 任何重载函数。

我消除了更改函数名称的歧义, 但我想知道是否有可能避免 这个错误在未来不依赖模板 论证推导。 在这种情况下,我如何指定 do_something() 的模板参数,可能不引用函数指针? 我没有丝毫的想法明确表达:

use_funct<-没有参数的那个->(do_something);

您可以将函数包装在 lambda 中,或者在将函数指针转换为您要调用的重载类型后传递函数指针,或者显式指定模板参数:

use_funct([](){ do_something (); });
use_funct(static_cast<void(*)()>(do_something));
use_funct<void()>(do_something);

将其包装在 lambda 中的优点是可以将重载决策推迟到 use_func。例如:

void do_something(int) {}

void do_something(double) {}

template<typename F> void use_funct(F funct) {   
    funct(1);    // calls do_something(int)
    funct(1.0);  // calls do_something(double)
}

int main() {   
    use_funct([](auto x){ do_something (x); });
}

[...] possibly without referring to a function pointer?

我不确定你的意思或你为什么要避免这种情况。 void() 是函数的类型,不是函数指针。如果您关心拼写类型,可以使用别名:

using func_type = void();
use_funct<func_type>(do_something);