Подтвердить что ты не робот

Как проверить, существует ли файл перед созданием нового файла

Я хочу ввести некоторое содержимое в файл, но сначала хочу проверить, существует ли файл с именем, которое я хочу создать. Если это так, я не хочу создавать какой-либо файл, даже если файл пуст.

Моя попытка

bool CreateFile(char name[], char content[]){
     std::ofstream file(name);
     if(file){
         std::cout << "This account already exists" << std::endl;
        return false;
     }
     file << content;
     file.close();
     return true;
}

Есть ли способ сделать то, что я хочу?

4b9b3361

Ответ 1

Предполагая, что это нормально, что операция не является атомарной, вы можете сделать:

if (std::ifstream(name))
{
     std::cout << "File already exists" << std::endl;
     return false;
}
std::ofstream file(name);
if (!file)
{
     std::cout << "File could not be created" << std::endl;
     return false;
}
... 

Обратите внимание, что это не работает, если вы запускаете несколько потоков, пытаясь создать один и тот же файл, и, конечно же, не помешаете второму процессу "вмешаться" в создание файла, потому что у вас TOCTUI. [Мы сначала проверяем, существует ли файл, а затем его создаем, но кто-то другой мог создать его между проверкой и созданием - если это важно, вам нужно будет сделать что-то еще, что не переносится.

Еще одна проблема заключается в том, что у вас есть разрешения, такие как файл не читается (поэтому мы не можем его открыть для чтения), но можно записать, он перезапишет файл.

В случаях MOST ни одна из этих вещей не имеет значения, потому что все, о чем вы заботитесь, говорит кому-то, что "у вас уже есть такой файл" (или что-то в этом роде) в "лучшем усилителе" подхода.

Ответ 2

вы также можете использовать Boost.

 boost::filesystem::exists( filename );

он работает для файлов и папок.

И у вас будет реализация, близкая к чему-то готовому для С++ 14, в котором файловая система должна быть частью STL (см. здесь).

Ответ 4

Попробуйте это (скопированный-ish из Erik Garrison: fooobar.com/questions/183911/...)

#include <sys/stat.h>

bool FileExists(char* filename) 
{
    struct stat fileInfo;
    return stat(filename, &fileInfo) == 0;
}

stat возвращает 0, если файл существует, и -1, если нет.

Ответ 5

Посмотрел немного, и единственное, что я нахожу, это использовать системный вызов open. Это единственная функция, которую я нашел, которая позволяет вам создать файл таким образом, который будет терпеть неудачу, если он уже существует.

#include <fcntl.h>
#include <errno.h>

int f=open(filename, O_WRONLY | O_CREAT | O_EXCL, S_IRUSR | S_IWUSR);
if (f < 0) {
  /* file exists or otherwise uncreatable
     you might want to check errno*/
}else {
  /* File is open to writing */
}

Обратите внимание, что вы должны предоставлять разрешения, так как вы создаете файл.

Это также устраняет любые условия гонки, которые могут быть

Ответ 6

С С++ 17 есть:

if (std::filesystem::exists(pathname)) {
   ...

Ответ 7

Я только что увидел этот тест:

bool getFileExists(const TCHAR *file)
{ 
  return (GetFileAttributes(file) != 0xFFFFFFFF);
}

Ответ 8

Самый простой способ сделать это - использовать ios :: noreplace.