Fastest way to check if a file exists using standard C++/C++11,14,17/C?
Well I threw together a test program that ran each of these methods 100,000 times, half on files that existed and half on files that didn't.
#include <sys/stat.h>
#include <unistd.h>
#include <string>
#include <fstream>
inline bool exists_test0 (const std::string& name) {
ifstream f(name.c_str());
return f.good();
}
inline bool exists_test1 (const std::string& name) {
if (FILE *file = fopen(name.c_str(), "r")) {
fclose(file);
return true;
} else {
return false;
}
}
inline bool exists_test2 (const std::string& name) {
return ( access( name.c_str(), F_OK ) != -1 );
}
inline bool exists_test3 (const std::string& name) {
struct stat buffer;
return (stat (name.c_str(), &buffer) == 0);
}
Results for total time to run the 100,000 calls averaged over 5 runs,
Method | Time |
---|---|
exists_test0 (ifstream) | 0.485s |
exists_test1 (FILE fopen) | 0.302s |
exists_test2 (posix access()) | 0.202s |
exists_test3 (posix stat()) | 0.134s |
What's the best way to check if a file exists in C?
Look up the access()
function, found in unistd.h
. You can replace your function with
if (access(fname, F_OK) == 0) {
// file exists
} else {
// file doesn't exist
}
Under Windows (VC) unistd.h
does not exist. To make it work it is necessary to define:
#ifdef WIN32
#include <io.h>
#define F_OK 0
#define access _access
#endif
You can also use R_OK
, W_OK
, and X_OK
in place of F_OK
to check for read permission, write permission, and execute permission (respectively) rather than existence, and you can OR any of them together (i.e. check for both read and write permission using R_OK|W_OK
)
Update: Note that on Windows, you can't use W_OK
to reliably test for write permission, since the access function does not take DACLs into account. access( fname, W_OK )
may return 0 (success) because the file does not have the read-only attribute set, but you still may not have permission to write to the file.
How to check if a file exists in C++ with fstream::open()
It says it sets the failbit if the file couldn't be opened. So you can check for that bit:
fileStream.open("logs.txt");
if (fileStream.fail()) {
// file could not be opened
}
Actually, just if (fileStream)
would work here as well, since ios
(a base class of ifstream
, ofstream
, and fstream
) has a conversion operator to bool
.
Don't worry about the failure exception. You can request exceptions to be thrown on failure by calling ios::exceptions
but by default exceptions are not thrown on failure.
Note that this doesn't tell you why the file couldn't be opened. It could be that the file didn't exist, that a directory in the path didn't exist, you don't have permission to open the file, your program has reached the limit on the number of files it can open, and so on. There is no portable way to determine the reason.
Is there a way to check if virtualisation is enabled on the BIOS using C++?
No, there is no way to detect virtualization support using only standard C++ facilities. The C++ standard library does not have anything related to hardware virtualization. (Its exposure of low level details like that is extremely limited.)
You would need to use OS-specific facilities to detect this.
Check if file exists, otherwise create a new one
Because of TOCTOU races, the best way to do this is to drop down a level and use open
, which, unlike fopen
, lets you specify "open this file for read and write, preserving existing contents, and create it if it doesn't already exist":
FILE *ensure_file(const char *fname)
{
int fd = open(fname, O_RDWR | O_CREAT, 0666);
if (fd == -1) {
perror(fname);
return 0;
}
return fdopen(fd, "r+");
}
problem in using fprintf_s(getting warnings) in c
When you try to open a file with fopen_s
function, it may or may not succeed, so you must check the return value of that invocation.
If for some reason, the file was not opened, then your file pointer variable, sttp
will not be initialized, hence the VS IDE is showing you the warning.
Modify your code, like below.
FILE* sttp;
if(0 == fopen_s(&sttp, "text.txt", "w") )
{
fprintf_s(sttp, "test");
fclose(sttp);
}
Related Topics
What Is the Proper Declaration of Main in C++
Order of Evaluation in C++ Function Parameters
How to Add "-L" (Ell) Compiler Flag in Cmake
What Is "Rvalue Reference For *This"
How to Remove Code Duplication Between Similar Const and Non-Const Member Functions
Meaning of Acronym Sso in the Context of Std::String
What Are the Evaluation Order Guarantees Introduced by C++17
Derived Template-Class Access to Base-Class Member-Data
Finding Current Executable'S Path Without /Proc/Self/Exe
If You Shouldn't Throw Exceptions in a Destructor, How to Handle Errors in It
Thou Shalt Not Inherit from Std::Vector
Post-Increment and Pre-Increment Concept
What Is External Linkage and Internal Linkage
How to Enable C++11/C++0X Support in Eclipse Cdt
Is It Better in C++ to Pass by Value or Pass by Reference-To-Const
Case-Insensitive String Comparison in C++
How to Reverse a String in Place in C or C++
Why Are Preprocessor Macros Evil and What Are the Alternatives