【发布时间】:2020-08-30 21:20:50
【问题描述】:
考虑以下 C++ 程序:
#include <cstdlib>
#include <functional>
#include <iostream>
#include <string>
#include <utility>
namespace {
template <typename Result, typename... Arg>
Result call_fn(std::function<Result(Arg...)> fn, Arg&&... arg) {
return fn(std::forward<Arg>(arg)...);
}
std::string test_fn(int, std::string*) {
return "hello, world!";
}
}
int main(int, char**) {
std::cout << call_fn(std::function(test_fn), 0, nullptr) << "\n";
return EXIT_SUCCESS;
}
这是一个人为的例子,但我在尝试实现与std::make_unique 模糊相似的东西时遇到了同样的问题。编译此程序时,出现以下错误:
$ clang++ -std=c++17 -Wall -Weverything -Werror -Wno-c++98-compat call_fn.cpp
call_fn.cpp:19:18: error: no matching function for call to 'call_fn'
std::cout << call_fn(std::function(test_fn), 0, nullptr) << "\n";
^~~~~~~
call_fn.cpp:9:8: note: candidate template ignored: deduced conflicting types for parameter 'Arg' (<int, std::__cxx11::basic_string<char> *> vs. <int, nullptr_t>)
Result call_fn(std::function<Result(Arg...)> fn, Arg&&... arg) {
^
1 error generated.
问题似乎是指针参数的类型推断为nullptr_t,而不是std::string*。我可以通过添加static_cast 或通过将模板参数显式指定为call_fn 来“解决”这个问题,但我觉得这种冗长程度令人反感。
有没有办法修改call_fn的定义,使得类型推导对指针参数更有效?
【问题讨论】:
标签: c++ template-argument-deduction