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

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


当前回答

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

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

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

其他回答

下面是获取执行应用程序的完整路径的代码:

变量声明:

char pBuf[256];
size_t len = sizeof(pBuf); 

窗口:

int bytes = GetModuleFileName(NULL, pBuf, len);
return bytes ? bytes : -1;

Linux:

int bytes = MIN(readlink("/proc/self/exe", pBuf, len), len - 1);
if(bytes >= 0)
    pBuf[bytes] = '\0';
return bytes;

对于Win32, GetCurrentDirectory应该做到这一点。

下面的操作在macOS 10.15.7上运行得很好

brew install boost

main.cpp

#include <iostream>
#include <boost/filesystem.hpp>

int main(int argc, char* argv[]){
  boost::filesystem::path p{argv[0]};
  p = absolute(p).parent_path();
  std::cout << p << std::endl;
  return 0;
}

编译

g++ -Wall -std=c++11 -l boost_filesystem main.cpp

从c++ 11开始,使用实验文件系统,c++ 14- c++ 17以及使用正式文件系统。

application.h:

#pragma once

//
// https://en.cppreference.com/w/User:D41D8CD98F/feature_testing_macros
//
#ifdef __cpp_lib_filesystem
#include <filesystem>
#else
#include <experimental/filesystem>

namespace std {
    namespace filesystem = experimental::filesystem;
}
#endif

std::filesystem::path getexepath();

application.cpp:

#include "application.h"
#ifdef _WIN32
#include <windows.h>    //GetModuleFileNameW
#else
#include <limits.h>
#include <unistd.h>     //readlink
#endif

std::filesystem::path getexepath()
{
#ifdef _WIN32
    wchar_t path[MAX_PATH] = { 0 };
    GetModuleFileNameW(NULL, path, MAX_PATH);
    return path;
#else
    char result[PATH_MAX];
    ssize_t count = readlink("/proc/self/exe", result, PATH_MAX);
    return std::string(result, (count > 0) ? count : 0);
#endif
}

If you fetch the current directory when your program first starts, then you effectively have the directory your program was started from. Store the value in a variable and refer to it later in your program. This is distinct from the directory that holds the current executable program file. It isn't necessarily the same directory; if someone runs the program from a command prompt, then the program is being run from the command prompt's current working directory even though the program file lives elsewhere.

getcwd是一个POSIX函数,所有POSIX兼容平台都支持它。你不需要做任何特殊的事情(除了在Unix上包含正确的头文件unistd.h和在windows上包含direct.h)。

由于您正在创建一个C程序,它将链接到默认的C运行时库,该库由系统中的所有进程链接(避免特别设计的异常),默认情况下它将包含这个函数。CRT从来不被认为是一个外部库,因为它为操作系统提供了基本的标准兼容接口。

在windows上,getcwd函数已弃用,而支持_getcwd。我觉得你可以这样用。

#include <stdio.h>  /* defines FILENAME_MAX */
#ifdef WINDOWS
    #include <direct.h>
    #define GetCurrentDir _getcwd
#else
    #include <unistd.h>
    #define GetCurrentDir getcwd
 #endif

 char cCurrentPath[FILENAME_MAX];

 if (!GetCurrentDir(cCurrentPath, sizeof(cCurrentPath)))
     {
     return errno;
     }

cCurrentPath[sizeof(cCurrentPath) - 1] = '\0'; /* not really required */

printf ("The current working directory is %s", cCurrentPath);