xcode 使用 c++17 的 `filesystem` 在我的 mac os x high sierra 上不起作用

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/49577343/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-15 10:35:54  来源:igfitidea点击:

`filesystem` with c++17 doesn't work on my mac os x high sierra

c++xcodeidec++17

提问by Lu4

I'm following this tutorial:

我正在关注本教程:

http://www.bfilipek.com/2017/08/cpp17-details-filesystem.html

http://www.bfilipek.com/2017/08/cpp17-details-filesystem.html

to checkout new c++ filesystemfeature. However I'm unable to compile even minimal example on my machine:

签出新的 C++filesystem功能。但是,我什至无法在我的机器上编译最小的示例:

#include <string>
#include <iostream>
#include <filesystem>

namespace fs = std::filesystem;

int main()
{
    std::string path = "/";

    for (auto & p : fs::directory_iterator(path))
        std::cout << p << std::endl;
}

I was using XCode, CLion and command line while trying to compile it but nothing works, I have Version 9.3 (9E145) with (seemingly proper) project settings, none of which work:

我在尝试编译时使用了 XCode、CLion 和命令行,但没有任何效果,我有 9.3 版(9E145)和(看似正确的)项目设置,但没有一个工作:

enter image description hereenter image description here

在此处输入图片说明在此处输入图片说明

Here is my CMakeLists.txtfile for CLion:

这是我CMakeLists.txt的 CLion 文件:

cmake_minimum_required(VERSION 3.8)

project(FileSystem2)

set(CMAKE_CXX_STANDARD 17)

add_executable(FileSystem2 main.cpp)

Here is an output from > gxx --version:

这是来自的输出> gxx --version

enter image description here

在此处输入图片说明

Nevertheless this is what I get as an output from my IDEs:

尽管如此,这是我从 IDE 中得到的输出:

enter image description hereenter image description hereenter image description here

在此处输入图片说明在此处输入图片说明在此处输入图片说明

What am I doing wrong, it looks to me that my compiler should support c++17?

我做错了什么,在我看来我的编译器应该支持 c++17?



Edit

编辑

As per Owen Morgan's answer I've installed clang (actual install command was brew install llvm) but it now complains about absence of string.h. Any thoughts?

根据欧文摩根的回答,我已经安装了 clang(实际安装命令是brew install llvm),但它现在抱怨没有string.h. 有什么想法吗?

回答by Owen Morgan

The compiler shipped with Xcode supports C++17 languagefeatures but not C++17 standard library features. Looking at your screenshot you will see the standard library support goes up to C++11, and Apple has not yet shipped a version of clang that has stdlib support for either C++14 or C++17.

Xcode 附带的编译器支持 C++17语言功能,但不支持 C++17 标准库功能。查看您的屏幕截图,您将看到标准库支持上升到 C++11,而 Apple 尚未发布对 C++14 或 C++17 具有 stdlib 支持的 clang 版本。

However hope is not lost! You can download the newest version of clang from the brew package manager.

然而希望并没有消失!您可以从 brew 包管理器下载最新版本的 clang。

brew install clang

Then you can compile by setting your cmake compiler flags to be your custom brew version and then running that.

然后你可以通过将你的 cmake 编译器标志设置为你的自定义 brew 版本然后运行它来编译。

Here is a link how to do that: http://antonmenshov.com/2017/09/09/clang-openmp-setup-in-xcode/

这是一个如何做到这一点的链接:http: //antonmenshov.com/2017/09/09/clang-openmp-setup-in-xcode/

Edit:

编辑:

After installing llvmyou will need to link your llvm path into your current shell. I have a shell script that I use at work to get this set up properly. Hope this helps.

安装后,llvm您需要将 llvm 路径链接到当前的 shell。我有一个 shell 脚本,我在工作中使用它来正确设置。希望这可以帮助。

#!/bin/bash
brew update
brew install --with-toolchain llvm # llvm but with all the headers
xcode-select --install # installs additional headers that you might be mimssing.
echo 'export PATH="/usr/local/opt/llvm/bin:$PATH"' >> ~/.bash_profile # exports the custom llvm path into the shell 
sudo ln -s /usr/local/opt/llvm/bin/clang++ /usr/local/bin/clang++-brew # optional but I like to have a symlink set.

Edit 2:

编辑2:

Clang 6.0 doesn't have <filesystem>included on macOS yet, however you can get <experimental/filesystem>, and link against -lc++experimental, and use std::experimental::filesysteminstead of std::filesystem.

Clang 6.0 尚未<filesystem>包含在 macOS 中,但是您可以获取<experimental/filesystem>、链接到-lc++experimental,并使用std::experimental::filesystem代替std::filesystem

Final command line invocation:

最终的命令行调用:

Owen$ /usr/local/Cellar/llvm/6.0.0/bin/clang++ fs.cpp -std=c++1z -L /usr/local/Cellar/llvm/6.0.0/lib/ -lc++experimental

Owen$ /usr/local/Cellar/llvm/6.0.0/bin/clang++ fs.cpp -std=c++1z -L /usr/local/Cellar/llvm/6.0.0/lib/ -lc++experimental

Edit 3:

编辑3:

Current clang version 7.0.1 supports either <filesystem>or <experimental/filesystem>. In any case, the compiler command line must be slightly different:

当前的 clang 版本 7.0.1 支持<filesystem><experimental/filesystem>。无论如何,编译器命令行必须略有不同:

Owen$ /usr/local/Cellar/llvm/7.0.1/bin/clang++ main.cpp -std=c++1z -L /usr/local/Cellar/llvm/7.0.1/lib/ -lc++fs

with -lc++fsinstead of -lc++experimental. Optionally, you can replace-std=c++1zwith -std=c++17as well.

-lc++fs代替-lc++experimental。或者,您可以替换-std=c++1z使用-std=c++17为好。

回答by aiusepsi

If you don't want to change compiler to use std::filesystem (because it's a pain), another option is to use the Boost Filesystemlibrary. Boost Filesystem was the basis for std::filesystem, so for most uses it's completely compatible with std::filesystem.

如果您不想将编译器更改为使用 std::filesystem (因为它很痛苦),另一种选择是使用Boost Filesystem库。Boost Filesystem 是 std::filesystem 的基础,因此对于大多数用途,它与 std::filesystem 完全兼容。

Setting up Boost is pretty easy if you're using CMake. Just brew install boostthen in your CMakeLists.txt do something like:

如果您使用 CMake,则设置 Boost 非常简单。就在brew install boost那时,在您的 CMakeLists.txt 中执行以下操作:

# Boost
set(boost_min_ver 1.50.0)
set(boost_libs system filesystem)
find_package(Boost ${boost_min_ver})

if(Boost_FOUND)
    find_package(Boost ${boost_min_ver} COMPONENTS ${boost_libs})
endif()

target_link_libraries(your_target ${Boost_LIBRARIES})

The extra verbosity in finding Boost helps, I find, to suppress some warnings CMake would otherwise throw at you.

我发现,查找 Boost 的冗长有助于抑制 CMake 否则会向您抛出的一些警告。

Then in your C++ code:

然后在你的 C++ 代码中:

#include <boost/filesystem.hpp>
namespace fs = boost::filesystem;

If you're feeling very fancy, you can use the __has_includedefine to check if the standard filesystem include is available, and if so, set namespace fs = std::filesystemand fallback to Boost only if the std version isn't available.

如果您觉得很花哨,您可以使用__has_include定义来检查标准文件系统包含是否可用,如果可用,则namespace fs = std::filesystem仅在标准版本不可用时才设置并回退到 Boost。

回答by Gulrak

As std::filesystem support on macOS with the official compiler and Xcode 11.1 is now limited to Catalina/10.15 deployment targets and up, I want to humbly add ghc::filesystemby myself as an additional option. It was written because I wanted to use std::filesystem on macOS, so it might be worth a try.

由于带有官方编译器和 Xcode 11.1 的 macOS 上的 std::filesystem 支持现在仅限于 Catalina/10.15 部署目标及更高版本,我想谦虚地自己添加ghc::filesystem作为附加选项。写它是因为我想在 macOS 上使用 std::filesystem,所以它可能值得一试。

It is a header-only feature complete implementation of std::filesystem for macOS, Linux and Windows, works from C++11 to C++17, and it tries to stay close to the standard. It might be a less heavy dependency than boost (if you don't use that already). In the simplest form, just drop the main header file next to your source, include filesystem.hpp, eventually add

它是适用于 macOS、Linux 和 Windows 的 std::filesystem 的仅标头功能的完整实现,适用于 C++11 到 C++17,并且它试图保持接近标准。它可能是一个比 boost 更轻的依赖(如果你还没有使用它的话)。在最简单的形式中,只需将主头文件放在源旁边,包括 filesystem.hpp,最后添加

namespace fs = ghc::filesystem;

and use it like it is std::filesystem. It is also possible to separate parts of the implementation into a cpp by using the additional header files, the readme explains how to do that.

并像 std::filesystem 一样使用它。也可以通过使用额外的头文件将实现的部分分离到 cpp 中,自述文件解释了如何做到这一点。

Note:It was implemented with utf8-everywhere in mind, but has an option to enable std::wstring interfaces on Windows as specified by the standard. The std::string_view related functions are limited to C++17, as it doesn't include a backport of std::string_view.
More details can be found in the readme under differences in api.

注意:它是用 utf8-everywhere 实现的,但有一个选项可以在 Windows 上启用标准指定的 std::wstring 接口。std::string_view 相关函数仅限于 C++17,因为它不包括 std::string_view 的向后移植。
更多细节可以在 api 差异下的自述文件中找到。