在日志中记录文件名和行号是一种常见的调试技术,可以帮助开发者快速定位问题。这是通过编译器提供的预定义宏和编程技巧实现的。以下是实现方法:
1. 使用预定义宏
C/C++编译器提供了几个特殊的预定义宏:
-
__FILE__
:展开为当前源文件的字符串路径(如"sylar/scheduler.cc") -
__LINE__
:展开为当前代码行的整数(如233) -
__func__
(或__FUNCTION__
):展开为当前函数名的字符串
2. 在日志宏中的典型实现
通常会将日志功能封装为宏,自动捕获位置信息。例如:
// 示例:带文件名和行号的日志宏
#define LOG_INFO(msg) \
std::cout << "[" << __FILE__ << ":" << __LINE__ << "] " << msg << std::endl
// 使用方式
LOG_INFO("Task started"); // 输出: [sylar/scheduler.cc:233] Task started
3. 更完善的实现(现代C++)
实际项目中可能会结合更多特性(如日志级别、格式化等):
// 高级日志宏示例
#define LOG(level, fmt, ...) \
log_impl(level, __FILE__, __LINE__, fmt, ##__VA_ARGS__)
// 底层实现函数
void log_impl(LogLevel level, const char* file, int line,
const char* fmt, ...) {
// 获取时间戳、格式化消息等...
printf("[%s][%s:%d] ", timestamp, file, line);
// 处理可变参数...
}