将变参函数参数无成本地转发到另一个变参函数

时间:2018-09-04 06:20:23

标签: c++ c++11 optimization variadic-functions perfect-forwarding

我有一个可变参数LogDebug用于写日志。日志记录有两种模式。 在大多数情况下,我的应用程序将可变参数传递给另一个可变函数LogDebugEx,因此该路径需要优化。 具体来说,我在callgrind图上的某些请求vsnprintf花费了38%。请注意,此功能针对单个请求多次调用。

void LogDebug(const char* zFormat, ...)
{
    char zDesc[5000];
    va_list ap;
    va_start(ap, zFormat);
    vsnprintf(zDesc, 5000, zFormat, ap);  // Need to optimize in remode mode.
    va_end(ap);

    if (m_logMode == LOG_MODE_LOCAL)    // Does not need to optimize this mode.
    {
        // This mode is not interested.
    }
    else // m_logMode == LOG_MODE_REMOTE, critical path
    {
        LogDebugEx("%s", zDesc);   // Forwarded to new variadic function
    }
}

问题:在转发到zDesc函数之前,我需要避免将整个参数列表复制到LogDebugEx数组中。 我有什么办法可以将LogDebug的正向可变参数传递到LogDebugEx函数中?

在不更改对LogDebug的函数调用的情况下,任何其他可行的方法也可以。 我有C++11支持的编译器GCC 4.9.3

1 个答案:

答案 0 :(得分:9)

如果我们有c ++ 11,为什么还要弄乱可变参数列表?

#include <utility>

extern enum {LOG_MODE_LOCAL, LOG_MODE_REMOTE} m_logMode;

extern void LogDebugEx(const char*, ...);

template<class...Args>
void LogDebug(const char* zFormat, Args&&...args)
{

    if (m_logMode == LOG_MODE_LOCAL)    // Does not need to optimize this mode.
    {
        char zDesc[5000];
        snprintf(zDesc, 5000, zFormat, args...);  
        // do what you have to do here
    }
    else // m_logMode == LOG_MODE_REMOTE, critical path
    {
        LogDebugEx(zFormat, std::forward<Args>(args)...);   // Forwarded to new variadic function
    }
}