【问题标题】:C++20 Template Template Concept SyntaxC++20 模板模板概念语法
【发布时间】:2021-07-03 16:51:45
【问题描述】:

对于概念,C++20 提供了很好的语法,例如

template<typename T>
concept SomeConcept = true; // stuff here


template<typename T>
requires SomeConcept<T>
class Foo;

template<SomeConcept T>
class Foo;

这两种概念限制类的方式是等价的,但后者更简洁。

如果我现在有一些模板模板概念,例如

template<template<typename> typename T>
concept SomeOtherConcept = true; // stuff here

template<template<typename> typename T>
requires SomeOtherConcept<T>
class Foo;

我不知道没有要求条款的非冗长(简洁/简短)语法,例如

template<template<typename> SomeotherConcept T>
class Foo;

template<template<SomeOtherConcept> typename T>
class Foo;

没用,所以

声明这样一个模板模板类的正确语法是什么?对模板模板参数有概念限制?

【问题讨论】:

    标签: c++ templates c++20 c++-concepts


    【解决方案1】:

    声明这样一个模板模板类的正确语法是什么?对模板模板参数有概念限制?

    编写依赖于模板模板参数或非类型模板参数的约束的唯一方法是使用 requires-clause。较短的 type-constraint 语法仅适用于约束类型的概念(因此得名 type-constraint):

    template <typename T> concept Type = true;
    template <template <typename...> class Z> concept Template = true;
    template <auto V> concept Value = true;
    
    // requires-clause always works
    template <typename T> requires Type<T> struct A { };
    template <template <typename...> class Z> requires Template<Z> struct B { };
    template <auto V> requires Value<V> struct C { };
    
    // type-constraint only for type concepts
    template <Type T> struct D { };
    
    // abbreviated function template definitely only for type concepts
    void e(Type auto x);
    

    【讨论】:

      【解决方案2】:

      这是我以前用过的一个技巧。

      使用noop-like 函数在主表达式中定义一个 lambda,如下所示:

      void noop(auto) {}
      
      //...
      
      template<typename T>
      concept SomeConcept = true;
      
      /*
      template <template<typename>SomeConcept T>
      struct Example {};
      */ //does not work
      
      template <template<typename>typename T>
        requires requires() {
          {
            noop(
              []<typename TArg> requires SomeConcept<typename T<TArg>> (){}
            )
          };
        }
      struct Example {};
      

      【讨论】:

      • 如此庞大的requires requires ...requires SomeConcept&lt;T&gt; 好多少?
      • @Caleth template&lt;typename&gt;typename 不能转换为 typename。所以它比你建议的更好,因为你的建议甚至没有编译。
      • 对不起,我的意思是requires SomeOtherConcept&lt;T&gt;,这是被问到的问题
      • @Caleth requires SomeOtherConcept&lt;T&gt; 与写template &lt;SomeOtherConcept T&gt; 相同,这不是所询问的内容。您可以指定template&lt;typename&gt;typename T 的“返回”具有一个遵循SomeOtherConcept 概念的静态成员来解决此问题。 (需要静态成员破解,因为template&lt;typename&gt;template&lt;typename&gt;typename 无效)
      • @Vye,如果Ttemplate&lt;template&lt;typename&gt; typename T&gt; 则不会。 template&lt;SomeOtherConcept T&gt; 无效,因为它不是类型概念
      猜你喜欢
      • 2020-05-14
      • 2022-09-29
      • 1970-01-01
      • 2021-07-12
      • 1970-01-01
      • 1970-01-01
      • 2022-01-18
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多