std :: ofstream,在写入之前检查文件是否存在

cwe*_*ton 34 c++ fstream std stream ofstream

我正在使用C++ 在Qt应用程序中实现文件保存功能.

我正在寻找一种方法来检查所选文件是否已经存在,然后写入它,以便我可以向用户提示警告.

我正在使用std::ofstream,我不是在寻找Boost解决方案.

Ric*_*ico 64

这是我最喜欢的折叠功能之一,我可以随时使用它.

#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;
}
Run Code Online (Sandbox Code Playgroud)

如果您没有立即将其用于I/O,我发现这比尝试打开文件更有品味.

  • +1但是`return stat(filename.c_str(),&buf)!= 1;`相当紧凑. (13认同)
  • 不是非标准的吗? (6认同)
  • 我在2.67GHz Intel Xeon上计时.上面的stat方法花了0.93微秒来确认存在500MB文件.下面的ifstream方法在同一个文件上花了17.4微秒.为了告诉没有文件存在,stat需要0.72微秒,ifstream需要2.4微秒. (6认同)
  • +1表示使用stat而非打开文件只是为了关闭它. (3认同)

ret*_*n 0 39

bool fileExists(const char *fileName)
{
    ifstream infile(fileName);
    return infile.good();
}
Run Code Online (Sandbox Code Playgroud)

到目前为止,这种方法是最短且最便携的方法.如果使用不是很复杂,这是我想要的.如果您还想提示警告,我会在主要部分进行.

  • 说明:使用ifstream构造函数尝试打开文件以进行读取.当函数返回并且ifstream超出范围时,它的析构函数将隐式关闭文件(如果文件存在且打开成功). (7认同)
  • 除了它做错了事:它检查文件是否可以打开,而不是它是否存在。如果访问权限不允许用户访问它,该函数将错误地声明该文件不存在,因为它将无法打开它进行读取。 (2认同)

HC4*_*ica 9

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
Run Code Online (Sandbox Code Playgroud)

请注意,如果是现有文件,则会以随机访问模式打开它.如果您愿意,可以关闭它并以追加模式或截断模式重新打开它.


Roi*_*ton 6

对于std::filesystem::existsC++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.
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

也可以看看std::error_code

如果您想检查正在写入的路径是否实际上是常规文件,请使用std::filesystem::is_regular_file.


NPE*_*NPE 5

尝试::stat()(在 中声明<sys/stat.h>