【问题标题】:Can I static assert that an entity is instantiation of a template class without enforcing any/all template arguments?我可以在不强制任何/所有模板参数的情况下静态断言实体是模板类的实例化吗?
【发布时间】:2021-03-01 21:48:18
【问题描述】:

可能标题里的问题太笼统了,因为好奇所以笼统

但这个通用问题源于一个具体的、不那么通用的用例。

我最初编写了一个函数来处理类 A 的 2 个元素的数组:

auto /* return type is not relevant */ fun(std::array<A,2>& a) {
    // ... do things...
}

然后我决定将功能扩展到 a 有 3 个元素的情况。使用std::vector&lt;A&gt; 处理此问题不是一种选择,因为这两个场景永远不会相互交互,我也不需要push_back on/pop_back from a

为了让两者协同工作,我放弃了显式参数类型,转而依赖auto

auto /* ditto */ fun(auto& a) {
    // ... do things, which depend on `auto` having deduced a `std::array<A,N>` for some `N`...
}

但是这样做有点不可取,因为:

  • 代码的自我记录比它可能的要少:其他人(或一个月内的我自己)将不得不查看fun 的内部,以了解它使用a,假设它是@987654333 @通用N;
  • 错误消息比它们可能的不太清楚:错误将类似于 没有函数与此调用匹配,而我希望错误是 此函数有效与std::arrayAs

我能做的是将autostatic_asserting 保留在astd::array&lt;A,2&gt;std::array&lt;A,3&gt; 的函数的第一行,但将来我可能想处理此案@ 987654342@也是。

所以如果有办法断言变量a 是给定模板类的实例,我只是在徘徊,例如std::array并非全部指定了模板参数。

一般来说,给定一个像这样的模板类,

template<typename A, int n, typename B, int m>
class C { /* impl */ };

是否可以断言变量a 的类型为C&lt;some_class,some_number,?,?&gt;

【问题讨论】:

  • 看来你的问题和this一样。或者至少是相关的。

标签: c++ templates template-meta-programming static-assert


【解决方案1】:

只需将您的函数设为模板即可。 N会自动推导出来。

template<std::size_t N>
auto fun(std::array<A,N>& a) {
   // ... do things, which depend on `auto` having deduced a `std::array<A,N>` for some `N`...
}

【讨论】:

  • 如果fun 不是函数而是 lambda,这是否有效?抱歉,但为了简化问题,我忘记指定 在我的情况下 fun 实际上是 lamda
  • @Enrico 你可以用 lambdas 做的一切,你也可以不用 lambdas,所以也许你可以考虑一下。
  • @Enrico 然后,阅读:stackoverflow.com/q/54126204/580083
  • @DanielLangr,我接受 user253751 的回答,因为它确实回答了我的(有缺陷的)问题。但是,比你链接那个,知道这非常非常有用。
  • @Enrico - 从 C++20 开始,您可以使用模板 lambda 并编写一些东西 []&lt;std::size_t N&gt;(std::array&lt;A, N&gt; &amp; a){ /* .... */ }
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-07-17
  • 2017-10-03
  • 2013-02-11
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多