c ++ 11可变参数args,带有函数默认参数值

时间:2015-11-12 13:28:58

标签: c++11 variadic-templates

我有包装器调用模板函数N次:

<form method="post" action="#">
    <p><label for="u_name">Username: </label><input type="text" name="u_name" value=""></p>

    <p><label for="u_pass">Password: </label><input type="password" name="u_pass" value=""></p>

    <p><button type="submit" name="go">login</button></p>
</form>

一切正常,直到我使用默认参数传递函数:

template <std::uint16_t N, typename F, typename  ... Args>
inline typename std::result_of<F && (Args &&...)>::type retry_n(F && f, Args&& ... ax)
{
    for (auto i = 0; i < N; ++i)
    {
        try
        {
            return std::forward<F>(f)(std::forward<Args>(ax)...);
        }
        catch (const some_except &e){ /*ignore exception for a while*/ }
    }
    throw;//re-raise
}

如何在没有明确说明的情况下使用默认参数?

1 个答案:

答案 0 :(得分:2)

默认参数不是函数签名的一部分,不参与模板类型推导。因此,无论何时将f传递给retry_n<>F的类型都会推断为int(int, int, int),因此本地f属于后一种类型,默认值为参数现在不在流程中。你唯一的解决方案是使用你想要直接测试的函数,而不必推断它的类型,比如@Johannes Schaub - litb的注释,或者,如果你的编译器不支持通用lambda(C ++ 14),请将它包装起来使用可变参数模板operator()

进入仿函数
struct functor
{
    template<typename... T>
    int operator()(T&&... params)
    {
        return f(std::forward<T>(params)...);
    }  
};

并将其用作

retry_n<10>(functor{}, 1, 2);