C ++ 17是2017年批准的C ++标准的名称。它基于以前的C ++ 14标准,改进了核心语言和标准库,并添加了一些新的语言功能。
浏览我的代码,我发现了一个部分 - 我认为 - 应该是编译时错误,但实际上编译和运行良好。一个简化版本是: 类基类 { 民众: 基数(int i) {} }; ...
我正在开发一个 C++ 代码库,该代码库提供了一些库的源文件,我无法违反某些准则或更改库逻辑和范例,例如我'...
如何使 `if constexpr` 变得对 SFINAE 友好?
我有一个使用“经典”SFINAE 的代码。 template auto power(M const& elem) -> decltype(std::norm(elem)) { return std::norm(elem); } 模板 我有一个使用“经典”SFINAE 的代码。 template<class M> auto power(M const& elem) -> decltype(std::norm(elem)) { return std::norm(elem); } template<class M, class = std::enable_if_t<(M::rank::value >= 1)>> auto power(M const& array) { return accumulate(begin(array), end(array), 0.0, [](auto const& alpha, auto const& omega) { return alpha + power(omega); }); } 这是一个递归(跨维度或等级)“幂”函数,通过计算较低维度子元素的幂,最终给出元素的平方和。 现代 C++ 鼓励使用 if constexpr 以避免使用 SFINAE,如下所示。 template<class M> auto power(M const& array) { if constexpr(M::rank::value >= 1) { return accumulate(begin(array), end(array), 0.0, [](auto const& alpha, auto const& omega) { return alpha + power(omega); }); } else { return std::norm(array); } } 问题在于,if constexpr中的表达式似乎首先必须是有效的表达式。 元素没有名为 rank 的成员类型,因此会出现编译错误。 如果表达式无效,是否有技巧可以使 if constexpr 谓词? C++20 及更新版本: if constexpr (requires{requires std::bool_constant</*condition*/>::value;}) 还有一个不太详细的选项: if constexpr (requires{requires /*condition*/;}) 但是后者更糟糕,因为如果编译时不知道条件,它会导致硬错误,而前者只是返回 false。 前者在标准库中使用(另请参阅在嵌套需求中,为什么使用requires bool_constant<X>::value;而不是requires X;?)。 C++17: 使用检测惯用语: #include <type_traits> namespace detail { template <typename ...P> struct void_type {using type = void;}; template <typename DummyVoid, template <typename...> typename A, typename ...B> struct is_detected : std::false_type {}; template <template <typename...> typename A, typename ...B> struct is_detected<typename void_type<A<B...>>::type, A, B...> : std::true_type {}; } template <template <typename...> typename A, typename ...B> inline constexpr bool is_detected = detail::is_detected<void, A, B...>::value; 然后: template <typename M> using CheckRank = std::enable_if_t<M::rank::value >= 1>; if constexpr (is_detected<CheckRank, M>)
是否通过值显式捕获此值强制复制此值,即使它未在 lambda 主体中使用?
如果我在类成员函数中有一个 lambda,并且它实际上不需要捕获 this (例如,它不使用任何成员变量),则显式捕获 this (按值)会强制复制 thi. ..
`std::可选`工厂函数,具有保证复制省略和`私有`构造函数,没有密钥习惯用法
考虑以下模式: 类部件 { 私人的: 显式小部件(依赖&&); 民众: 静态 std::可选 make(std::文件系统::路径 p) { 标准::
删除了模板类构造函数,但有一个专门化与 clang 和 gcc 的行为不同
我正在尝试理解这种行为。 我创建了一个模板类,其中删除了构造函数,然后将其专门用于 int 类型。我的目标是仅为 int 创建实例(
动机 随着 C++ 获得了可选值(在 C++17 中),现在通常需要编写以下内容: 如果条件成立,则用某个表达式初始化我的变量;如果条件
动机 随着 C++ 获得了可选值(在 C++17 中),现在通常需要编写以下内容: 如果条件成立,则用某个表达式初始化我的变量;如果条件
我正在编写一个分配器,它将对齐作为模板参数以及对齐: 模板 类 AlignedAllocator { 民众: 使用 value_type ...
我有一个枚举类,例如: 枚举类状态{ S1, S2, S3, S4 }; 每当我做出可能使用此类的 switch/case 语句时,我
std::move 于 std::vector 类型的 std::Optional
在 std::Optional> 上执行 std::move 是否安全?它没有给我任何编译器或运行时错误,但想知道这是否有效。这是我的示例代码
std::is_invocable 可以在 C++11 中模拟吗?
我想使用std::is_invocable,但是我们使用的是c++11标准,而is_invocable仅在c++17中可用。 有什么方法可以使用 c++11 模拟功能吗? 谢谢你
我正在用最新的 clang++ 玩弄 c++17 中的折叠表达式。 我尝试使用它来实现数组的 less 运算符,我想将其用于固定大小的字符串。 这里是...
为什么我不应该将带有按引用捕获的 lambda 传递给 std::thread 构造函数?
我编写了一个计时器类,但它没有按照我需要的方式工作。谁能告诉我这有什么问题吗? 模板 上课定时器 { 民众: 计时器(D 时段、C&am...
我编写了一个计时器类,但它没有按照我需要的方式工作。谁能告诉我这有什么问题吗? 模板 上课定时器 { 民众: 计时器(D 时段、C&am...
我想要一个连接 string_views 的折叠表达式函数。但我尝试过的代码不起作用。我究竟做错了什么 ? 模板 我想要一个折叠表达式函数来连接 string_views。但我尝试过的代码不起作用。我做错了什么? template<typename Allocator, typename Char, typename Traits> auto sv_concat( std::basic_string_view<Char, Traits> svs ... ) { basic_string<Char, Traits, Allocator> str; str.reserve( (svs.length() + ...) ); ((str += svs), ...); return str; } 这是 clang++ 18 个错误: test.cpp:14:31: error: pack expansion does not contain any unexpanded parameter packs 14 | str.reserve( (svs.length() + ...) ); | ~~~~~~~~~~~~ ^ test.cpp:15:17: error: pack expansion does not contain any unexpanded parameter packs 15 | ((str += svs), ...); | ~~~~~~~~~~~~ ^ 您的代码中没有参数包。我将只讨论这个问题。可变参数模板可用于实现可变参数函数,非可变参数模板则不能(除了 c 省略号)。 在可变参数模板中,您可以限制模板的多种类型全部相同,或者是同一模板的所有实例。然而,让我们从更简单的开始...... 而不是 std::string,我在示例中使用了一些带有单个模板参数的 Foo。因为我知道我需要使用部分专业化,所以我使用类模板 bar 代替函数模板。 template <typename T> struct foo {}; template <typename ... T> struct bar; template <typename ...U> struct bar<foo<U>...> { void operator()() { std::cout << sizeof...(U); } }; 可以添加的其他专业化,bar只能使用作为foo实例化的类型进行实例化。 另一种途径是对特征进行部分特化: template <typename T> struct is_foo : std::false_type {}; template <typename U> struct is_foo<foo<U>> : std::true_type {}; template <typename T> constexpr bool is_foo_v = is_foo<T>::value; 并用它来限制bar。 SFINAE 因为我是老派: template <typename ... T> auto bar() -> std::enable_if_t< std::conjunction_v<is_foo<T>...> > { std::cout << sizeof...(T);} 现场演示 有了概念,你就有了更好的方法来做同样的事情,但原则上它会做同样的事情。
我尝试执行检查参数是否与特定值匹配的函数。 我认为知道如何使用递归或 std::initializer_list 来做到这一点,但我想用折叠来做到这一点。这是非工作代码:
我正在使用 SDL2 库为 2D RPG 游戏编写 C++ 程序。我有一个名为 Entity 的类,它有一个名为 worldY 的属性: 类实体 { 民众: ... // 坐标世界:la ...
我尝试读取作为 zip 存档一部分的二进制文件。因此我用 Poco::Zip 打开了 zip 存档。然后我按块读取二进制文件 结构头 { uint64_t 标签; uint32_t
使用 C 风格字符串初始化 std::string_view
std::string_view 对象仅具有对诸如 std::string 之类的对象的视图,并且修改用于初始化 string_view 的字符串的值将使该对象无效。 现在,如果我初始化一个字符串...