当前位置: 首页 > 知识库问答 >
问题:

理解void_t和detect_if

逄皓轩
2023-03-14

我正在学习模板元编程,最近,我在CPP会议上看到了一个关于void_t的演讲。不久之后,我发现了检测成语。

然而,我仍然很难理解其中的任何一个(尤其是检测习惯用法,因为它基于void_t)。我看了这篇博文,还有这篇stackoverflow的帖子,对我有一点帮助,但是我还是有一些疑问。

如果我的理解是正确的,如果void_t中的表达式无效,它将使用以下表达式被SFINAEd除名:

template< class, class = std::void_t<> >
struct has_type_member : std::false_type { };

因为class在这里是一个默认的模板参数,可以表示任意数量的参数,而与它们的类型无关。甚至有必要说class等于std::void_t吗

template< class, class = void >
struct has_type_member : std::false_type { };

如果没有,为什么?

但是,如果表达式有效,则此表达式将称为计算为 void:

template< class T >
struct has_type_member<T, std::void_t<typename T::type>> : std::true_type { };

为什么一个有效的表达式会被计算为无效,这对我们有什么帮助?另外,为什么表达式需要有效才能匹配void_t?

共有1个答案

叶鸿煊
2023-03-14

好吧,我并不是说我自己已经完全理解了这一切,但我会尽我所能回答:

因为类在这里是一个默认的模板参数,可以表示任意数量的参数,独立于它们的类型?

近。此模板将使用一个或两个模板参数匹配任何实例化,因此所有表单has_type_member

  • class匹配任何类型。但这并不特别(您也可以编写class T,您只是不需要名称,因为您不在声明中引用它)每个模板最初都匹配所有类型,并且只能通过参数的数量来区分。通常,我们要么通过一些SFINAE-魔术(如enable_if)来约束,要么通过稍后的部分模板规范来更好地拟合。
  • class=val匹配所有类型,如上所述,也根本没有类型,因为如果我们没有参数,ull会填充。

我们只会将此模板实例化为has_member_type

为什么一个有效的表达式会被计算为无效,这对我们有什么帮助?另外,为什么表达式需要有效才能匹配void_t?

我已经回答了第一个问题的第二部分。关于第一个:想想<code>void_t</code>的定义:

template<class...>
using void_t = void;

所以,匹配所有东西,而不管类型和数字,不是吗?实际上,它只匹配有效类型,如果不匹配,它将如何潜在地使用此类型?(我知道它不使用类型,但它必须能够。它不能使用无效类型)。因此,如果传递的模板参数有效,它将为我们提供void。因此在我们的用例中:

如果< code>T具有成员类型< code>T::type,则< code>T::type是有效类型,而< code>void_t

如果我们没有类型成员呢?则表达式<code>T::type<code>无效,<code>void_

甚至有必要说class等于std::void_ t吗

template< class, class = void >
struct has_type_member : std::false_type { };

如果没有,为什么?

是的,它会,它也在谈话中完成。void_t

 类似资料:
  • 我观看了Walter Brown在Cppcon14上关于现代模板编程的演讲(第一部分,第二部分),他介绍了他的SFINAE技术。 示例: 给定一个简单的变量模板,如果所有模板参数都格式良好,则计算结果为: 存在 格式良好 有效,并计算为 2. 不存在 格式错误,以静默方式失败(sfinae) ,因此丢弃此模板

  • 我对node.js比较熟悉,编写一个程序时需要承诺异步API调用。我有一个关于执行一些示例代码的问题,这是我在研究中偶然发现的。 下面的代码(根据我的理解)将访问一个API,等待响应,然后将该响应解析为承诺。这是迭代完成的,每个创建的承诺都被传递到一组承诺中。最终,对许诺数组调用promise.all()和.then(),将执行更多代码来迭代数组并将图像添加到页面中。 这里我不理解的是promis

  • 当我通过Visual Basic运行它时,我知道结果。我很难理解的是它是如何实现的。 我的工作方式: 和我认为是“值的名称”,可以与例如x或y互换使用。与和相同。 第一个dec_result是8.60 第二个dec_result是8.75 为什么33/5位变成了6位?它显示为占位符指定的小数位数和数据类型double指定的小数位数。 应该是括号前指定的整数,而占位符也表示以数字形式提供值,不带小数

  • 一般来说,和的调用如下: 步骤是 > 线程2锁定互斥锁并调用,从而解锁互斥锁 在线程1中,调用,并再次锁定互斥锁 现在在线程2中,在调用之后,

  • 这几年来,我阅读了很多WebKit和Chromium的代码,也给它们提交过一些的代码补丁包(patch),一个感觉是代码量真的很大,常常看了这块忘了那块;另一个感觉是文档真的很少,特别是WebKit(chromium有不少设计文档,但是还不够)。 这让我觉得非常痛苦,常常摸不着头绪。鉴于自己的经历,觉得很有必要把阅读代码后的理解和总结记录下来,一来帮助自己回忆,二来可以分享给其他人,三来方便大家一

  • 所以我试图弄清楚如何使用Realm,Moya和ObjectMapper。 我使用Moya向我的API发出请求。我使用Realm将返回的数据保存在本地数据库中。并且我使用ObjectMapper将JSON对象映射到校正领域变量。 然而,现在我遇到了一个问题,我不确定如何解码JSON响应以便将其通过映射器。 下面是我的莫亚密码: 错误发生在这一行: 类如下所示: 我明白为什么我会犯这个错误,但我不知道