繁体   English   中英

C++模板function指针类型推导

[英]C++ template function pointer type deduction

我有以下代码

using my_map_t = std::map<int, Object<double>>;
using my_map_iterator_t = my_map_t::iterator;


template <typename FWD, typename Func>
void inner(my_map_t& map, int key, FWD&& obj, Func emplacer) {
        emplacer(map, key, std::forward<FWD>(obj));
}
  

my_map_t map;

template <typename FWD>
void outer(my_map_t& map, int key, FWD&& obj)
{
        auto lambda = [](my_map_t& m, int k, FWD&& o) {
                m.emplace(k, std::forward<FWD>(o));
        };

        inner(map, key, std::forward<FWD>(obj), lambda);
}

编译无痛。 所以这意味着他自动推导出inner function 的模板参数。 但是,如果我引入 function 指针我需要指定 function 指针模板参数,否则编译器会抱怨

using my_map_t = std::map<int, Object<double>>;
using my_map_iterator_t = my_map_t::iterator;


template <typename FWD, typename Func>
void inner(my_map_t& map, int key, FWD&& obj, Func emplacer) {
        emplacer(map, key, std::forward<FWD>(obj));
}

template <typename FWD, typename Func>
void(*fp)(my_map_t&, int, FWD&&, Func) = &inner;


my_map_t map;

template <typename FWD>
void outer(my_map_t& map, int key, FWD&& obj)
{
        auto lambda = [](my_map_t& m, int k, FWD&& o) {
                m.emplace(k, std::forward<FWD>(o));
        };

        (*fp<FWD, decltype(lambda)>)(map, key, std::forward<FWD>(obj), lambda);
}

为什么在 function 指针的情况下,参数推导不再起作用? 我犯了什么错误吗? 有没有办法实现更好的语法?

增加注释

我需要使用 function 指针,因为我有一些具有相同签名的inner 让我们称它们为inner1inner2inner3 它们被一些外部 function 调用

void outer(...) {
     if(...) {

         inner1(...)
     } else if (...) {
     
         inner2(...)
     } else {

         inner3(...)
     }
     some_long_task(...)
}

现在在我的情况下, outer function 被循环调用。 if中的检查可能很耗时,并且它们独立于outer function 的参数。 我在想,当some_long_task正在执行时,设置一个 function 指针指向right的 function inner1inner2inner3利用一些 cpu 并行性,这样,新的循环开始,我不必浪费时间进行 if 检查.

template <typename FWD, typename Func>
void(*fp)(my_map_t&, int, FWD&&, Func) = &inner;

不是正常的 function 指针。 这就是所谓的变量模板 当你有一个变量模板时,为了引用一个特定的实例,你必须指定模板参数。 为了证明这一点,考虑

template <typename T>
constexpr T pi = T(3.1415926535897932385L);  

你不能只做cout << pi ,因为我们不知道使用哪个pi 同样的情况发生在

(*fp<FWD, decltype(lambda)>)(map, key, std::forward<FWD>(obj), lambda);

这里fp需要<FWD, decltype(lambda)>以便编译器知道要引用哪个特定的fp实例。 它甚至在评估 function 调用之前就必须这样做,因为它需要根据 function 检查参数。

我们不需要指定参数的是像CTAD这样的未来,但适用于 function 指针变量模板。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM