Bet*_*moo 102 c c++ dynamic-compilation line-numbers c-preprocessor
出于调试目的,我可以在C/C++编译器中获取行号吗?(某些编译器的标准方式或特定方式)
例如
if(!Logical)
    printf("Not logical value at line number %d \n",LineNumber);
    // How to get LineNumber without writing it by my hand?(dynamic compilation)
Jul*_*rau 166
您应该使用预处理器宏__LINE__和__FILE__.它们是预定义的宏,是C/C++标准的一部分.在预处理期间,它们分别由一个常量字符串替换,该字符串包含一个表示当前行号的整数和当前文件名.
其他预处理变量:
__func__:函数名称(这是C99的一部分,并非所有C++编译器都支持它)__DATE__ :一串形式"Mmm dd yyyy"__TIME__ :形式为"hh:mm:ss"的字符串您的代码将是:
if(!Logical)
  printf("Not logical value at line number %d in file %s\n", __LINE__, __FILE__);
Bri*_*ndy 62
作为C++标准的一部分,您可以使用一些预定义的宏.C++标准的第16.8节定义了__LINE__宏.
__LINE__:当前源行的行号(十进制常量).
__FILE__:源文件的假定名称(字符串文字).
__DATE__:源文件的转换日期(字符串文字...)
__TIME__:源文件的转换时间(字符串文字...)
__STDC__:是否__STDC__预定义
__cplusplus:名称__cplusplus定义为值199711L时编译C++翻译单元
所以你的代码是:
if(!Logical)
  printf("Not logical value at line number %d \n",__LINE__);
Som*_*mer 19
您可以使用与printf()具有相同行为的宏,但它还包括调试信息,如函数名称,类和行号:
#include <cstdio>  //needed for printf
#define print(a, args...) printf("%s(%s:%d) " a,  __func__,__FILE__, __LINE__, ##args)
#define println(a, args...) print(a "\n", ##args)
这些宏应该与printf()的行为相同,同时包含类似java stacktrace的信息.这是一个主要的例子:
void exampleMethod() {
    println("printf() syntax: string = %s, int = %d", "foobar", 42);
}
int main(int argc, char** argv) {
    print("Before exampleMethod()...\n");
    exampleMethod();
    println("Success!");
}
这导致以下输出:
main(main.cpp:11)在exampleMethod()之前...
exampleMethod(main.cpp:7)printf()语法:string = foobar,int = 42
main(main.cpp:13)成功!
C++20 通过使用std::source_location提供了一种新方法来实现这一点。这是目前在海湾合作委员会的铛可访问std::experimental::source_location与#include <experimental/source_location>。
宏的问题__LINE__是,如果你想创建例如一个输出当前行号和消息的日志函数,你总是必须__LINE__作为函数参数传递,因为它在调用站点被扩展。像这样的东西:
void log(const std::string msg) {
    std::cout << __LINE__ << " " << msg << std::endl;
}
将始终输出函数声明的行而不是log实际调用的行。另一方面,std::source_location你可以这样写:
#include <experimental/source_location>
using std::experimental::source_location;
void log(const std::string msg, const source_location loc = source_location::current())
{
    std::cout << loc.line() << " " << msg << std::endl;
}
在这里,loc用指向log调用位置的行号初始化。
您可以在此处在线试用。
尝试__FILE__并__LINE__。
您可能还会发现__DATE__并且__TIME__有用。
不过,除非您必须在客户端调试程序并因此需要记录这些信息,否则您应该使用正常调试。
对于那些可能需要它的人,可以使用“FILE_LINE”宏轻松打印文件和行:
#define STRINGIZING(x) #x
#define STR(x) STRINGIZING(x)
#define FILE_LINE __FILE__ ":" STR(__LINE__)