pau*_*doo 35 c++ directory winapi
我正在尝试创建一个带有目录(C:\foo\bar,或..\foo\bar\..\baz,或\\someserver\foo\bar)名称的函数,并根据需要创建目录,以便创建整个路径.
我自己尝试了一个非常天真的实现,它似乎是一个字符串处理的噩梦.有/vs \,有网络共享的特殊情况开始\\(也不能尝试mkdir()路径的前两个级别,即机器名和共享名),并且存在\.\可以存在的类型废话在一条路上.
在C++中是否存在一种简单的方法?
Fre*_*abe 48
如果您不需要支持Windows 2000之前的Windows版本,则可以使用SHCreateDirectoryEx函数.考虑一下:
int createDirectoryRecursively( LPCTSTR path )
{
return SHCreateDirectoryEx( NULL, path, NULL );
}
// ...
if ( createDirectoryRecursively( T("C:\\Foo\\Bar\\Baz") ) == ERROR_SUCCESS ) {
// Bingo!
}
Run Code Online (Sandbox Code Playgroud)
如果使用这样的shell32.dll API成为一个问题,您总是可以使用其他东西(可能是手动连线循环)重新实现上面的createDirectoryRecursively函数.
cta*_*cke 11
这是一个没有外部库的版本,因此只支持Win32,并且在所有版本的Windows中都有该功能(包括Windows CE,我需要它):
wchar_t *path = GetYourPathFromWherever();
wchar_t folder[MAX_PATH];
wchar_t *end;
ZeroMemory(folder, MAX_PATH * sizeof(wchar_t));
end = wcschr(path, L'\\');
while(end != NULL)
{
wcsncpy(folder, path, end - path + 1);
if(!CreateDirectory(folder, NULL))
{
DWORD err = GetLastError();
if(err != ERROR_ALREADY_EXISTS)
{
// do whatever handling you'd like
}
}
end = wcschr(++end, L'\\');
}
Run Code Online (Sandbox Code Playgroud)
这是我编写的一个函数,它迭代地创建了一个文件夹树.这是主要功能:
#include <io.h>
#include <string>
#include <direct.h>
#include <list>
// Returns false on success, true on error
bool createFolder(std::string folderName) {
list<std::string> folderLevels;
char* c_str = (char*)folderName.c_str();
// Point to end of the string
char* strPtr = &c_str[strlen(c_str) - 1];
// Create a list of the folders which do not currently exist
do {
if (folderExists(c_str)) {
break;
}
// Break off the last folder name, store in folderLevels list
do {
strPtr--;
} while ((*strPtr != '\\') && (*strPtr != '/') && (strPtr >= c_str));
folderLevels.push_front(string(strPtr + 1));
strPtr[1] = 0;
} while (strPtr >= c_str);
if (_chdir(c_str)) {
return true;
}
// Create the folders iteratively
for (list<std::string>::iterator it = folderLevels.begin(); it != folderLevels.end(); it++) {
if (CreateDirectory(it->c_str(), NULL) == 0) {
return true;
}
_chdir(it->c_str());
}
return false;
}
Run Code Online (Sandbox Code Playgroud)
该folderExists程序如下:
// Return true if the folder exists, false otherwise
bool folderExists(const char* folderName) {
if (_access(folderName, 0) == -1) {
//File not found
return false;
}
DWORD attr = GetFileAttributes((LPCSTR)folderName);
if (!(attr & FILE_ATTRIBUTE_DIRECTORY)) {
// File is not a directory
return false;
}
return true;
}
Run Code Online (Sandbox Code Playgroud)
我测试上述函数的示例调用如下(并且它可以工作):
createFolder("C:\\a\\b\\c\\d\\e\\f\\g\\h\\i\\j\\k\\l\\m\\n\\o\\p\\q\\r\\s\\t\\u\\v\\w\\x\\y\\z");
Run Code Online (Sandbox Code Playgroud)
此功能尚未经过非常彻底的测试,我不确定它是否适用于其他操作系统(但可能与一些修改兼容).我现在使用的Visual Studio 2010带Windows 7.
使用 C++17,这可以很容易地使用std::filesystem::create_directories().
例子:
#include <filesystem>
...
const char* path = "C:\\foo\\bar";
std::filesystem::create_directories(path);
Run Code Online (Sandbox Code Playgroud)
SHCreateDirectory函数可以做到这一点.但该文档声明它可以在更高版本的Windows中被弃用.
来自MSDN
注意此功能可通过Windows XP Service Pack 2(SP2)和Microsoft Windows Server 2003获得.它可能会在后续版本的Windows中更改或不可用.
| 归档时间: |
|
| 查看次数: |
47434 次 |
| 最近记录: |