我正在使用模块的 C++20 项目中使用 spdlog 库。
我将 spdlog 封装在我的单例记录器类中,因为我不希望 spdlog 暴露给客户端,以防有一天我将其换成不同的日志库。但现在我想要一个宏,当不在分发配置中时,它会调用我的单例的“Trace()”方法,并且在分发中是无操作的。我的宏在 Log.h 中是这样定义的:
#if defined(TS_DEBUG) || defined(TS_RELEASE)
#define TS_LOG_TRACE(...) ::ThreeSpace::Logger::Trace(__VA_ARGS__)
#else
#define TS_LOG_TRACE(...)
#endif
然后宏会将参数转发到我的公共记录器方法。我的方法只是将这些参数传递给 spdlog 的 trace() 方法,该方法具有以下签名:
template<typename... Args>
inline void trace(format_string_t<Args...> fmt, Args &&...args);
客户会这样使用它:
TS_LOG_TRACE("First value is {} and second value is {}", 42, 45);
我花了很长时间才弄清楚如何编写我的 Logger 单例的 trace() 方法。
我试过了
template<typename... Args>
void Logger::Trace(std::format_string<Args...> fmt, Args &&...args)
{
GetInstance()->trace(fmt, std::forward<Args>(args)...);
}
但它给了我错误
Error C2664: 'void spdlog::logger::trace<_Ty,_Ty>
fmt::v9::basic_format_string<char,int,int>,_Ty &&,_Ty &&)':
cannot convert argument 1 from 'std::basic_format_string<char,int,int>' to
'fmt::v9::basic_format_string<char,int,int>'
ThreeSpace C:\Dev\ThreeSpace\Core\src\Logger.cppm 90
我觉得我很接近,但无法弄清楚。我做错了什么?
感谢您的帮助!
编辑: 所以我发现如果我像这样定义模板化方法:
template<typename... Args>
void Logger::Trace(std::format_string<Args...> fmt, Args &&...args)
{
std::string str = std::format(fmt, std::forward<Args>(args)...);
std::cout << str;
}
它可以工作并将预期的消息打印到控制台。但如果我将方法的主体更改为此,它就会失败:
GetInstance()->trace(fmt, std::forward<Args>(args)...);