Detect if a file exists?

Is there a way to simply do this?

Edit: Also looking for a way to detect what the extension is.

Edit 2: It turns out I don't need a way to detect what the extension is.
Last edited on
Yes. Try to open the file, and check the errors. Windows gui code has tools to search for a file built in. Unix has tools to do this as well, but I don't know if its better to link in a library or to just ask the OS on unix.

The extension ... is part of the file name you used... if you do not know it, and used a wildcard search, the results of the search will give the name and therefore its extension.

Under Windows you can use the FindFirstFile function. To get the extension of the file take all the characters after the last colon.
1
2
3
4
5
6
7
8
9
10
11
12
#include <windows.h>
#include <string>

bool FileExists(const std::string& filename)
{
  WIN32_FIND_DATAA fd = {0};
  HANDLE hFound = FindFirstFileA(filename.c_str(), &fd);
  bool retval = hFound != INVALID_HANDLE_VALUE;
  FindClose(hFound);

  return retval;  
}

https://msdn.microsoft.com/en-us/library/windows/desktop/aa364418(v=vs.85).aspx
I'm trying to make my program OS-independent. It also turns out that I don't need extension handling.

Edit: I'm blind apparently. Your solution @jonnin appears to be a good one - gonna try it now.
Last edited on
If a file couldn't be opened because it didn't exist or whatever...

1
2
3
4
5
6
7
8
#include <iostream>
#include <fstream>

int main()
{
    if (std::fstream{FILE_NAME}) std::cout << "file exists\n";
    else std::cerr << "file couldn\'t be opened (not existing or failed to open)\n";
}

File extension

1
2
3
4
5
6
7
8
9
10
#include <iostream>
#include <string>

int main()
{
    const std::string file_name{"main.cpp"};
    if (file_name.find('.') == std::string::npos) std::cout << "no file extension\n";
    else if (file_name.find_last_of('.') == file_name.length() - 1) std::cout << ".\n";
    else std::cout << file_name.substr(file_name.find_last_of('.') + 1) << '\n';
}
Last edited on
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
#include <iostream>
#include <iomanip>

// http://en.cppreference.com/w/cpp/experimental/fs
#include <experimental/filesystem>
namespace fs = std::experimental::filesystem ;

// see: http://www.boost.org/doc/libs/1_63_0/libs/filesystem/doc/index.htm
// #include <boost/filesystem.hpp>
// namespace fs = boost::filesystem ;

int main()
{
    const fs::path this_file = __FILE__ ;
    std::cout << "path: " << this_file << '\n' 
              << "parent: " << this_file.parent_path() << '\n' 
              << "exists? " << std::boolalpha << fs::exists(this_file) << '\n' // true
              << "extension: " << std::quoted( this_file.extension().string() ) << '\n' ; // ".cpp"
}

http://rextester.com/IAUIW87887
http://rextester.com/MTSV94763
@JLBorges Too bad not everyone has access to this library (filesystem). It would simplify file handling a lot. Boost has it, but you need to link a shared library.
Everyone would have it (reasonably soon enough).
This TS has now been incorporated into the standard. (C++17).
@JLBorges Is C++17 officially out yet? I think it's soon this year if it's not out yet.

Wikipedia wrote:
is not expected to undergo any major changes before publication of the final standard later in the year
https://en.wikipedia.org/wiki/C%2B%2B17
Last edited on
No, it is in its final ISO balloting stage (voting by national standards bodies).

The July meeting of the ISO C++ committee was the first meeting for C++20 - they are already done with C++17.
If your environment has stat(), then you can use that:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
#include <iostream>
#include <sys/stat.h>
#include <errno.h>
#include <cstring>
int main()
{
    struct stat st;
    if (stat("myfile", &st) == 0) {
        std::cout << "myfile exists\n";
    } else {
        std::cout << "Can't stat myfile: errno=" << errno << ": "
             << strerror(errno) << '\n';
    }
}

If the files doesn't exist (as opposed to some other error), then stat will return non-zero and set errno to ENOENT.

Just because the file exists doesn't imply that you can open it.

For now the best would be to use boost or Kahless_9.
Topic archived. No new replies allowed.