我想在当前目录(即可执行文件所在的位置)创建一个文件。
我的代码:
LPTSTR NPath = NULL;
DWORD a = GetCurrentDirectory(MAX_PATH,NPath);
HANDLE hNewFile = CreateFile(NPath,GENERIC_WRITE,0,NULL,CREATE_ALWAYS,FILE_ATTRIBUTE_NORMAL,NULL);
我在使用GetCurrentDirectory()
时遇到了异常。
为什么会出现异常?
我想在当前目录(即可执行文件所在的位置)创建一个文件。
我的代码:
LPTSTR NPath = NULL;
DWORD a = GetCurrentDirectory(MAX_PATH,NPath);
HANDLE hNewFile = CreateFile(NPath,GENERIC_WRITE,0,NULL,CREATE_ALWAYS,FILE_ATTRIBUTE_NORMAL,NULL);
我在使用GetCurrentDirectory()
时遇到了异常。
为什么会出现异常?
TCHAR buffer[MAX_PATH] = { 0 };
GetModuleFileName( NULL, buffer, MAX_PATH );
#include <windows.h>
#include <string>
#include <iostream>
std::wstring ExePath() {
TCHAR buffer[MAX_PATH] = { 0 };
GetModuleFileName( NULL, buffer, MAX_PATH );
std::wstring::size_type pos = std::wstring(buffer).find_last_of(L"\\/");
return std::wstring(buffer).substr(0, pos);
}
int main() {
std::cout << "my directory is " << ExePath() << "\n";
}
GetModuleFileNameA
- MikhailGetModuleFileNameA
,如果使用Unicode,则使用GetModuleFileNameW
。 GetModuleFileName
(没有A
或W
)实际上是一个别名,它根据您的项目设置的字符集来使用,这就是大多数使用字符串的Win32 API方法的设置方式。因此,如果您的项目是Unicode,并且您的字符串也是Unicode,则只需调用GetModuleFileName
即可。如果您的项目是多字节的并且使用多字节字符串,则同样适用。 - RectangleEqualsfind_last_of()
方法,难道没有一些常量来定义目录名称中的分隔符,比如 ".../.../..." 或者 "........." 吗? - Dominiquefilesystem
库,它大大简化了这个过程。#include <filesystem>
#include <iostream>
std::filesystem::path cwd = std::filesystem::current_path() / "filename.txt";
std::ofstream file(cwd.string());
file.close();
cwd.string()
会返回一个与操作系统相关的路径字符串。很棒。GetCurrentDirectory
不为结果分配空间,这需要由你自己完成。
TCHAR NPath[MAX_PATH];
GetCurrentDirectory(MAX_PATH, NPath);
如果您想用C++的方式处理文件系统,请查看Boost.Filesystem库。
一个简单的方法是:
int main(int argc, char * argv[]){
std::cout << argv[0];
std::cin.get();
}
argv[]
基本上是一个包含你运行.exe文件时的参数数组,但第一个参数始终是可执行文件的路径。如果我构建它,控制台会显示:C:\Users\Ulisse\source\repos\altcmd\Debug\currentdir.exe
GetCurrentDirectory
返回进程的当前目录,即工作目录。 argv [0]
是可执行文件的路径。一个不同之处在于,在进程的生命周期中,工作目录可以更改,而 argv [0]
不能更改。 - Reza Ghodsi依我之见,这里有一些对Anon回答的改进建议。
#include <windows.h>
#include <string>
#include <iostream>
std::string GetExeFileName()
{
char buffer[MAX_PATH];
GetModuleFileName( NULL, buffer, MAX_PATH );
return std::string(buffer);
}
std::string GetExePath()
{
std::string f = GetExeFileName();
return f.substr(0, f.find_last_of( "\\/" ));
}
#include <iostream>
#include <stdio.h>
#include <dirent.h>
std::string current_working_directory()
{
char* cwd = _getcwd( 0, 0 ) ; // **** microsoft specific ****
std::string working_directory(cwd) ;
std::free(cwd) ;
return working_directory ;
}
int main(){
std::cout << "i am now in " << current_working_directory() << endl;
}
我没有正确使用GetModuleFileName。但我发现这个方法很有效。 只在Windows上测试过,还没有在Linux上试过 :)
在使用缓冲区之前,请不要忘记将其初始化为某些值。同样重要的是,为您的字符串缓冲区留出结尾空字符的空间。
TCHAR path[MAX_PATH+1] = L"";
DWORD len = GetCurrentDirectory(MAX_PATH, path);
WCHAR path[MAX_PATH] = {0};
GetModuleFileName(NULL, path, MAX_PATH);
PathRemoveFileSpec(path);
TCHAR s[100];
DWORD a = GetCurrentDirectory(100, s);
#include <windows.h>
using namespace std;
// The directory path returned by native GetCurrentDirectory() no end backslash
string getCurrentDirectoryOnWindows()
{
const unsigned long maxDir = 260;
char currentDir[maxDir];
GetCurrentDirectory(maxDir, currentDir);
return string(currentDir);
}
currentDir
- 一个类型为 "char *"
的参数与类型为 "LPWSTR"
(Unicode 编码)的参数不兼容。 - ZidoX