Frage
In einer Windows C-Anwendung möchte ich einen an eine Funktion übergebenen Parameter überprüfen, um sicherzustellen, dass der angegebene Pfad vorhanden ist. *
Wie überprüfen Sie, ob unter Windows in C ein Verzeichnis vorhanden ist?
* Ich verstehe, dass Sie in Rennbedingungen geraten können, in denen zwischen der Zeit, in der Sie die Existenz überprüfen, und der Zeit, in der Sie den Pfad verwenden, der nicht mehr existiert, aber ich kann damit umgehen.
Zusätzlicher Hintergrund
Wenn Sie explizit wissen, dass ein Verzeichnis vorhanden ist oder nicht, kann es schwierig werden, wenn Berechtigungen ins Spiel kommen. Es ist möglich, dass der Prozess beim Versuch, festzustellen, ob das Verzeichnis vorhanden ist, keine Berechtigungen zum Zugriff auf das Verzeichnis oder ein übergeordnetes Verzeichnis hat. Dies ist in Ordnung für meine Bedürfnisse . Wenn das Verzeichnis nicht vorhanden ist oder ich nicht darauf zugreifen kann, werden beide in meiner Anwendung als ungültiger Pfadfehler behandelt, sodass ich nicht unterscheiden muss. (Virtuelle) Bonuspunkte, wenn Ihre Lösung diese Unterscheidung vorsieht.
Jede Lösung in der C-Sprache, der C-Laufzeitbibliothek oder der Win32-API ist in Ordnung, aber im Idealfall möchte ich mich an häufig geladene Bibliotheken halten (z. B. Kernel32, User32 usw.) und Lösungen vermeiden, bei denen nicht standardmäßige Bibliotheken geladen werden (wie PathFileExists in Shlwapi.dll). Wieder (virtuelle) Bonuspunkte, wenn Ihre Lösung plattformübergreifend ist.
Antworten:
Mach so etwas:
BOOL DirectoryExists(LPCTSTR szPath) { DWORD dwAttrib = GetFileAttributes(szPath); return (dwAttrib != INVALID_FILE_ATTRIBUTES && (dwAttrib & FILE_ATTRIBUTE_DIRECTORY)); }
Die GetFileAttributes () -Methode ist in Kernel32.dll enthalten.
quelle
"C:\\"
, funktionieren GetFileAttributes, PathIsDirectory und PathFileExists nicht.Hier ist eine vollständig plattformunabhängige Lösung (unter Verwendung der Standard-C-Bibliothek).
Bearbeiten: Damit dies unter Linux kompiliert werden kann, ersetzen Sie es
<io.h>
durch<unistd.h>
und_access
durchaccess
. Verwenden Sie für eine echte plattformunabhängige Lösung die Boost FileSystem-Bibliothek.#include <io.h> // For access(). #include <sys/types.h> // For stat(). #include <sys/stat.h> // For stat(). bool DirectoryExists( const char* absolutePath ){ if( _access( absolutePath, 0 ) == 0 ){ struct stat status; stat( absolutePath, &status ); return (status.st_mode & S_IFDIR) != 0; } return false; }
Eine Windows-spezifische Implementierung, die sowohl MBCS- als auch UNICODE-Builds unterstützt:
#include <io.h> #include <sys/types.h> #include <sys/stat.h> #include <tchar.h> BOOL directory_exists( LPCTSTR absolutePath ) { if( _taccess_s( absolutePath, 0 ) == 0 ) { struct _stat status; _tstat( absolutePath, &status ); return (status.st_mode & S_IFDIR) != 0; } return FALSE; }
quelle
access
aus<unistd.h>
und es wäre nicht mit einem Unterstrich beginnen.)io.h
oder_access
(mit Unterstrich) auf anderen Plattformen./
anstatt überall. Ich bin verwirrt, aber anscheinend seien Sie vorsichtig mit POSIX-Pfaden und POSIX libc-Funktionen unter Win32.Wenn die Verknüpfung mit der Shell Lightweight-API (shlwapi.dll) für Sie in Ordnung ist, können Sie die PathIsDirectory-Funktion verwenden .
quelle
Eine weitere Option ist die Shell-Funktion PathFileExists ()
PathFileExists () -Dokumentation
Diese Funktion "Bestimmt, ob ein Pfad zu einem Dateisystemobjekt wie einer Datei oder einem Verzeichnis gültig ist."
quelle