【问题标题】:Conjunction of concepts before auto?汽车前的概念结合?
【发布时间】:2022-01-19 17:39:09
【问题描述】:

我正在学习 C++20 概念。有没有办法在auto 之前就地结合概念?例如,如果我有一个MutableGraph<G> 概念和一个VertexListGraph<G> 概念,我可以定义

template <typename G>
concept MutableVertexListGraph = MutableGraph<G> && VertexListGraph<G>;

然后做

MutableVertexListGraph auto g = ...;

但是当我希望它为这两个概念建模时,命名这个概念很烦人。如果我能做到就好了

MutableGraph && VertexListGraph auto g = ...; // && not allowed here.

甚至是类似的东西

template <typename T, concept... Concepts> // <- "concept" not allowed here.
concept ModelsAll = (Concepts<T> && ...);
...
ModelsAll<MutableGraph, VertexListGraph> auto g = ...;

我当然可以

MutableGraph auto g = ...;
requires { MutableGraph<decltype(g)>; };

缺乏对称性,或

auto g = ...;
requires { MutableGraph<decltype(g)>; MutableGraph<decltype(g)>; };

在声明行中缺少概念。

【问题讨论】:

  • 我不明白这个问题。你是在问你是否可以做到(我很确定你知道你不能),或者你为什么不能做到?
  • 我在问是否有办法做这样的事情,因为我猜测的东西似乎没有用。我怀疑答案是否定的,但是对于概念上可以做和不能做的各种事情,我不确定。 (或者,我想知道这是否是未来标准中可能需要的那种东西,比如MutableGraph &amp;&amp; VertexListGraph auto g = ...;(MutableGraph &amp;&amp; VertexListGraph) auto g = ...;。)
  • 你没有提到template&lt; class G &gt; requires (MutableGraph&lt;G&gt; and VertexListGraph&lt;G&gt;) T g = ...。是不是打字太多了?

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


【解决方案1】:

不,在将约束应用于推导变量定义的类型时,无法组合概念。

ConceptName auto variable = ...; 可读性强。 ConceptName 可能是不言自明的,它为变量定义留出了足够的空间。

Concept1 &amp;&amp; Concept2 &amp;&amp; Concept3 auto variable = ...; 可读性差很多。在那一点上,概念序列排挤了语句中真正重要的部分:变量声明。因此,将其拆分为多个语句更有意义:

auto variable = ...;
static_assert(Concept1<decltype(variable)> && Concept2<decltype(variable)> && Concept3<decltype(variable)>);

这涉及到非常不幸的decltype 使用量(额外的using 语句可以避免),但它确实将关注点分开,使variable 声明本身更具可读性。

【讨论】:

  • 这是有道理的。谢谢。我收集写作requires requires 是一种反模式,表明存在一个应该命名的概念。这可以说是相关的。对于我的特定示例,VertexListGraph 是“更基本的”,所以我可以看到 VertexListGraph auto g = ...; requires { MutableGraph&lt;decltype(g)&gt;; }; // It needs to be mutable too.
  • @Ben:您不能在变量声明上放置requires 约束。无论MutableGraph&lt;decltype(g)&gt; 的结果如何,requires 表达式都不会执行任何操作。它将评估为truefalse,并且您永远不会使用结果,因此它会被丢弃。这就是我使用static_assert 的原因。
  • 好收获。我注意到它已编译但没有检查它是否有效。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-07-26
  • 2015-02-07
  • 2015-10-09
  • 1970-01-01
  • 2018-10-13
  • 1970-01-01
相关资源
最近更新 更多