webentwicklung-frage-antwort-db.com.de

std :: ofstream, prüfe vor dem Schreiben, ob eine Datei existiert

Ich implementiere die Funktion zum Speichern von Dateien in einer Qt -Anwendung mit C++.

Ich suche nach einer Möglichkeit, um zu überprüfen, ob die ausgewählte Datei bereits vorhanden ist, bevor ich darauf schreibe, damit ich eine Warnung an den Benutzer senden kann.

Ich benutze ein std::ofstream und ich suche keine Boost Lösung.

33
cweston

Dies ist eine meiner Lieblingsfunktionen zum Verstauen, die ich für verschiedene Zwecke zur Verfügung habe.

#include <sys/stat.h>
// Function: fileExists
/**
    Check if a file exists
@param[in] filename - the name of the file to check

@return    true if the file exists, else false

*/
bool fileExists(const std::string& filename)
{
    struct stat buf;
    if (stat(filename.c_str(), &buf) != -1)
    {
        return true;
    }
    return false;
}

Ich finde das viel geschmackvoller, als zu versuchen, eine Datei zu öffnen, wenn Sie nicht sofort die Absicht haben, sie für E/A zu verwenden.

64
Rico
bool fileExists(const char *fileName)
{
    ifstream infile(fileName);
    return infile.good();
}

Diese Methode ist bislang die kürzeste und portabelste. Wenn die Verwendung nicht sehr raffiniert ist, ist dies eine, für die ich gehen würde. Wenn Sie auch eine Warnung anfordern möchten, würde ich das in der Hauptsache tun.

38
return 0
fstream file;
file.open("my_file.txt", ios_base::out | ios_base::in);  // will not create file
if (file.is_open())
{
    cout << "Warning, file already exists, proceed?";
    if (no)
    { 
        file.close();
        // throw something
    }
}
else
{
    file.clear();
    file.open("my_file.txt", ios_base::out);  // will create if necessary
}

// do stuff with file

Beachten Sie, dass eine vorhandene Datei im Direktzugriffsmodus geöffnet wird. Wenn Sie möchten, können Sie es schließen und im Anhänge- oder Kürzungsmodus erneut öffnen.

9
HighCommander4

Try ::stat() (deklariert in <sys/stat.h>)

4
NPE

Eine Möglichkeit wäre, stat() auszuführen und errno zu überprüfen.
Ein Beispielcode würde so aussehen:

#include <sys/stat.h>
using namespace std;
// some lines of code...

int fileExist(const string &filePath) {
    struct stat statBuff;
    if (stat(filePath.c_str(), &statBuff) < 0) {
        if (errno == ENOENT) return -ENOENT;
    }
    else
        // do stuff with file
}

Dies funktioniert unabhängig vom Stream. Wenn Sie es dennoch vorziehen, mit ofstream zu prüfen, prüfen Sie einfach mit is_open().
Beispiel:

ofstream fp.open("<path-to-file>", ofstream::out);
if (!fp.is_open()) 
    return false;
else 
    // do stuff with file

Hoffe das hilft. Vielen Dank!

2

Mit std::filesystem::exists von C++ 17:

#include <filesystem> // C++17
#include <iostream>
namespace fs = std::filesystem;

int main()
{
    fs::path filePath("path/to/my/file.ext");
    std::error_code ec; // For using the noexcept overload.
    if (!fs::exists(filePath, ec) && !ec)
    {
        // Save to file, e.g. with std::ofstream file(filePath);
    }
    else
    {
        if (ec)
        {
            std::cerr << ec.message(); // Replace with your error handling.
        }
        else
        {
            std::cout << "File " << filePath << " does already exist.";
            // Handle overwrite case.
        }
    }
}

Siehe auch std::error_code .

Wenn Sie überprüfen möchten, ob der Pfad, in den Sie schreiben, eine reguläre Datei ist, verwenden Sie std::filesystem::is_regular_file .

1
Roi Danton