2

我正在(切换到)<std::experimental::filesystem>在我的 C++14 代码中使用,我需要能够在 Linux 上使用 GCC 5.x(以及任何支持 C++14 的编译器,或者至少是相关版本)来构建它铿锵,msvc,也许还有icc)。

现在,当我链接时,我收到有关丢失所有文件系统相关符号的错误,例如:

foo.cpp:(.text+0x9cd): undefined reference to `std::experimental::filesystem::v1::__cxx11::path::_M_split_cmpts()'

现在,如果我“手动”添加对libstdc++fs

target_link_libraries(foo other_lib stdc++fs)

那么一切都很好 - 但我如何将其推广到任何支持 C++14 的编译器?

注意:我的相关部分CMakeLists.txt如下所示:

set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall" )
set(CMAKE_CXX_STANDARD 14)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
set(CMAKE_CXX_EXTENSIONS OFF)

add_library(bar src/bar.cpp)
add_executable(foo src/foo.cpp)
target_link_libraries(foo bar other_lib)

*(当我使用boost::filesystem它时,它反而更容易了——我只需要使用FindBoost.cmake产生的任何东西。)
**-Wall我猜,使用对于其他编译器来说也是一个问题。

4

1 回答 1

3

不幸的是,这正是它的预期用途。请参阅libstdc++ 文档的相关部分

GCC 5.3 包括由技术规范 ISO/IEC TS 18822:2015 定义的文件系统库的实现。因为这是一个实验性的库扩展,而不是 C++ 标准的一部分,所以它在单独的库 libstdc++fs.a 中实现,并且没有共享库。要使用该库,您应该包含并链接 -lstdc++fs。库实现在非 POSIX 平台上是不完整的,特别是 Windows 支持是基本的。

由于文件系统库的实验性质,通常对 ABI 稳定性和向后兼容性的保证不适用于它。无法保证任何标头中的组件在不同的 GCC 版本之间保持兼容。

(强调我的)

libstdc++fs仅在 GCC 下显式链接,您可以使用相关的 CMake 变量

target_link_libraries(foo other_lib)
if (CMAKE_CXX_COMPILER_ID STREQUAL GNU)
    target_link_libraries(foo stdc++fs)
endif()

或者,以更花哨的方式,

if (CMAKE_CXX_COMPILER_ID STREQUAL GNU)
    set(CXX_FILESYSTEM_LIBRARIES stdc++fs)
else()
    set(CXX_FILESYSTEM_LIBRARIES)
endif()
target_link_libraries(foo other_lib ${CXX_FILESYSTEM_LIBRARIES})
于 2018-05-04T10:44:01.350 回答