问题
I am writing a library (just for learning) which utilizes std::filesystem. It works fine on MSVC however by default LTS releases of Linux like Ubuntu ships with GCC 6.x and clang in the official repository is 3.8 which doesn't have std::filesystem instead I have to use std::experimental::filesystem. How may I workaround this problem so that I can support GCC 6, GCC 8+ (where std::filesystem works), Clang 3.8, latest Clang and MSVC? I am using CMAKE as my build system
回答1:
Conditional compilation may help:
#if(defined(_MSC_VER) or (defined(__GNUC__) and (7 <= __GNUC_MAJOR__)))
using n_fs = ::std::filesystem;
#else
using n_fs = ::std::experimental::filesystem;
#endif
回答2:
I fixed my problem in the following way:
I added the following bunch of code in the project's CMakeLists.txt file
if("${CMAKE_CXX_COMPILER_ID}" STREQUAL "GNU")
if(CMAKE_CXX_COMPILER_VERSION VERSION_LESS 5.4)
message(FATAL_ERROR "You are on an extremely old version of GCC. Please update your compiler to at least GCC 5.4, preferably latest")
elseif (CMAKE_CXX_COMPILER_VERSION VERSION_LESS 7.0)
message(WARNING "Old Verison of GCC detected. Using Legacy C++ support")
target_link_libraries(${PROJECT_NAME} -lstdc++fs)
target_compile_definitions(${PROJECT_NAME} PUBLIC LEGACY_CXX)
endif()
endif()
And in my CPP file, I did this:
#ifdef LEGACY_CXX
#include <experimental/filesystem>
namespace n_fs = ::std::experimental::filesystem;
#else
#include <filesystem>
namespace n_fs = ::std::filesystem;
#endif
Here's the commit if anyone want to refer to.
回答3:
"How may I workaround this problem" - by installing a newer compiler/standard library. Or by not using std::filesystem
.
For example, on RedHat and CentOS you can install devtoolset-8 to get access to a newer (and supported) compiler than what the base system provides. Other Linux distributions may have similar options.
You can also compile a newer compiler + std lib yourself from source. That's in itself not too difficult, but you need to be careful to then also ship the new libraries. And testing compatibility with the base distro libraries etc is on you.
You can also, as per @VTT's answer, use conditional compilation to fall back to std::experimental::filesystem
if that's all your toolchain supports and you are ok with that.
Of you don't want to change compiler and using std::experimental::filesystem
is not ok (or your compiler/standard library doesn't even support that), then your only option is to use OS native functions.
来源:https://stackoverflow.com/questions/55782902/stdfilesystem-and-stdexperimentalfilesystem-problem-in-different-compilers