C语言中可用的标准预定义宏__FILE__显示文件的完整路径。有办法缩短这条路吗?我的意思是
/full/path/to/file.c
我看到
to/file.c
or
file.c
C语言中可用的标准预定义宏__FILE__显示文件的完整路径。有办法缩短这条路吗?我的意思是
/full/path/to/file.c
我看到
to/file.c
or
file.c
当前回答
GCC 12将提供GNU C扩展宏__FILE_NAME__来获取编译文件的基名。
请参阅GCC文档,其中已经包含了这个宏:GCC -common_predefined_macros
GCC线程:Bug 42579 - [PATCH]支持获取文件basename
其他回答
对@red1ynx提议的轻微变化将创建以下宏:
#define SET_THIS_FILE_NAME() \
static const char* const THIS_FILE_NAME = \
strrchr(__FILE__, '/') ? strrchr(__FILE__, '/') + 1 : __FILE__;
在每一个。c(pp)文件中添加:
SET_THIS_FILE_NAME();
然后你可以引用THIS_FILE_NAME而不是__FILE__:
printf("%s\n", THIS_FILE_NAME);
这意味着每个.c(pp)文件执行一次构造,而不是每次引用宏时都执行。
它仅限于从.c(pp)文件中使用,不能从头文件中使用。
编译时没有办法做到这一点。显然,您可以在运行时使用C运行时实现它,正如其他一些答案所演示的那样,但是在编译时,当预处理器启动时,您就不走运了。
我刚刚想到了一个很好的解决方案,它可以同时使用源文件和头文件,非常有效,并且可以在所有平台的编译时工作,没有特定于编译器的扩展。此解决方案还保留了项目的相对目录结构,因此您可以知道文件在哪个文件夹中,并且只相对于项目的根目录。
其思想是用构建工具获取源目录的大小,并将其添加到__FILE__宏中,完全删除目录,只显示从源目录开始的文件名。
下面的例子是使用CMake实现的,但是没有理由它不能与任何其他构建工具一起工作,因为技巧非常简单。
在CMakeLists.txt文件中,定义一个宏,该宏具有到CMake上项目的路径长度:
# The additional / is important to remove the last character from the path.
# Note that it does not matter if the OS uses / or \, because we are only
# saving the path size.
string(LENGTH "${CMAKE_SOURCE_DIR}/" SOURCE_PATH_SIZE)
add_definitions("-DSOURCE_PATH_SIZE=${SOURCE_PATH_SIZE}")
在你的源代码中,定义一个__FILENAME__宏,它只是将源路径大小添加到__FILE__宏:
#define __FILENAME__ (__FILE__ + SOURCE_PATH_SIZE)
然后使用这个新宏而不是__FILE__宏。这是因为__FILE__路径总是以CMake源目录的路径开始。通过从__FILE__字符串中移除它,预处理器将负责指定正确的文件名,并且它都将相对于你的CMake项目的根。
如果你关心性能,这与使用__FILE__一样有效,因为__FILE__和SOURCE_PATH_SIZE都是已知的编译时常量,因此可以由编译器优化。
唯一会失败的地方是如果你在生成的文件上使用这个,而且它们在一个off-source build文件夹上。然后,您可能必须使用CMAKE_BUILD_DIR变量而不是CMAKE_SOURCE_DIR创建另一个宏。
因为使用的是GCC,所以可以利用
__BASE_FILE__这个宏扩展为主输入文件的名称,以C字符串常量的形式。这是源文件 在预处理器或C编译器的命令行中指定
然后在编译时通过更改源文件表示(完整路径/相对路径/basename)来控制显示文件名的方式。
Try
#pragma push_macro("__FILE__")
#define __FILE__ "foobar.c"
在源文件中的include语句之后,然后添加
#pragma pop_macro("__FILE__")
在源文件的末尾。