是否有一种平台不可知和文件系统不可知的方法来获取程序运行的目录的完整路径?不要与当前工作目录混淆。(请不要推荐库,除非它们是像clib或STL这样的标准库。)

(如果没有平台/文件系统不可知的方法,也欢迎在Windows和Linux中针对特定文件系统工作的建议。)


当前回答

在stdlib.h中像这样使用realpath():

char *working_dir_path = realpath(".", NULL);

其他回答

只是我的两美分,但下面的代码在c++ 17中不能移植吗?

#include <iostream>
#include <filesystem>
namespace fs = std::filesystem;

int main(int argc, char* argv[])
{
    std::cout << "Path is " << fs::path(argv[0]).parent_path() << '\n';
}

至少在Linux上对我有用。

根据前面的想法,我现在有:

std::filesystem::path prepend_exe_path(const std::string& filename, const std::string& exe_path = "");

与实现:

fs::path prepend_exe_path(const std::string& filename, const std::string& exe_path)
{
    static auto exe_parent_path = fs::path(exe_path).parent_path();
    return exe_parent_path / filename;
}

main()中的初始化技巧:

(void) prepend_exe_path("", argv[0]);

感谢@Sam Redway的argv[0]想法。当然,我知道当OP提出这个问题时,c++ 17还没有出现很多年。

如果你想要一种没有库的标准方式:不。标准中没有包含目录的整个概念。

如果您同意对接近标准库的某些(可移植的)依赖是可以的:使用Boost的文件系统库并请求initial_path()。

恕我直言,这是你能得到的最接近的结果,并且有良好的因果报应(Boost是一套完善的高质量库)

一个库解决方案(尽管我知道这不是要求的)。 如果你恰好使用Qt: QCoreApplication: applicationDirPath ()

我知道现在回答这个问题已经很晚了,但我发现没有一个答案像我自己的解决方案那样对我有用。一个非常简单的方法来获取路径从你的CWD到你的bin文件夹是这样的:

int main(int argc, char* argv[])
{
    std::string argv_str(argv[0]);
    std::string base = argv_str.substr(0, argv_str.find_last_of("/"));
}

您现在可以使用它作为相对路径的基。例如,我有这样的目录结构:

main
  ----> test
  ----> src
  ----> bin

我想把我的源代码编译到bin并写一个日志来测试,我可以把这一行添加到我的代码中。

std::string pathToWrite = base + "/../test/test.log";

我在Linux上尝试过这种方法,使用全路径,别名等,它工作得很好。

注意:

如果你是在windows中,你应该使用“\”作为文件分隔符,而不是“/”。你也需要转义这个,例如:

std::string base = argv[0].substr(0, argv[0].find_last_of("\\"));

我认为这应该工作,但还没有测试,所以评论将是感激如果它工作或修复如果不是。

文件系统TS现在是一个标准(gcc 5.3+和clang 3.9+都支持),所以你可以使用它的current_path()函数:

std::string path = std::experimental::filesystem::current_path();

在gcc(5.3+)包含文件系统,你需要使用:

#include <experimental/filesystem>

用-lstdc++fs标记链接你的代码。

如果你想在Microsoft Visual Studio中使用文件系统,请阅读本文。