当前位置: 首页 > news >正文

深入理解c++20 concepts

concepts在c20中被引入其作用是对模板参数进行约束极大地增强了c模板的功能。在c20之前如果希望获取类似的效果使用起来并不方便。没有concept时如何实现对模板参数进行约束static_assert我们可以使用static_assert去对模板类型T进行约束。如下所示12345678910111213#include type_traits#include iostreamtemplateclassTvoidtest(T a){static_assert(std::is_integralT());std::cout T is integral std::endl;}intmain(){test(10);testdouble(12.3);}但是该种方法不太好因为需要将static_assert嵌入到函数的内部这意味着即使类型不对模板还是成功的匹配上了只是在模板函数内部展开时出现编译错误。SFINAESFINAE是Substitution Failure Is Not An Error的缩写翻译过来的意思是替换失败并不是一个错误。SFINAE是模板元编程中常见的一种技巧如果模板实例化后的某个模板函数模板类对该调用无效那么将继续寻找其他重载决议而不是引发一个编译错误。因此一句话概括SFINAE就是模板匹配过程中会尝试各个重载模板直到所有模板都匹配失败才会认为是真正的错误。例如下面这个经典的例子123456789101112structTest {typedefintfoo;};templatetypenameTvoidf(typenameT::foo) {}// Definition #1templatetypenameTvoidf(T) {}// Definition #2intmain() {fTest(10);// Call #1.fint(10);// Call #2. Without error (even though there is no int::foo)// thanks to SFINAE.}fTest(10)最终将使用到第一个模板定义 而fint(10)最终将使用到第二个模板定义。SFINAE 原则最初是应用于上述的模板编译过程。后来被C开发者发现可以用于做编译期的决策配合sizeof可以进行一些判断类是否定义了某个内嵌类型、类是否包含某个成员函数等。例如STL中迭代器中的has_iterator_category。123456789templatetypenameTstructhas_iterator_category {structtwo {chara;charb; };templatetypenameCstatictwo test(typenameC::iterator_category*);templatetypenamestaticchar test(...);staticconstboolvalue sizeof(testT(nullptr)) sizeof(two);};enable_ifenable_if的出现使得SFINAE使用上更加方便进一步扩展了上面has_xxxis_xxx的作用。而enable_if实现上也是使用了SFINAE。enable_if的定义简单 即当_Test是true时将不会有type的类型定义而当_Test是false时将会有type的类型定义。1234567// STRUCT TEMPLATE enable_iftemplatebool_Test,class_Ty voidstructenable_if {};// no member type when !_Testtemplateclass_Tystructenable_iftrue, _Ty {// type is _Ty for _Testusingtype _Ty;};下面是利用enable_if去实现SFINAE的方式。12345678910111213141516171819202122#include type_traits#include iostreamtemplatetypenameTtypenamestd::enable_ifstd::is_integralT::value, T::typetest(T value){std::coutT is intergalstd::endl;returnvalue;}templatetypenameTtypenamestd::enable_if!std::is_integralT::value, T::typetest(T value){std::coutT is not intergalstd::endl;returnvalue;}intmain(){test(100);test(a);test(100.1);}可以看到SFINAE的主要实现了is_xxx和has_xxx的语义但是其语法并不简单对使用者有较高要求并且即便写正确了可读性也相对较差。有了concept之后如何使用声明concept声明一个concept的语法如下所示12templatetemplate-parameter-list concept concept-name constraint-expression;例如约束T是一个整形12templatetypenameTconcept integral std::is_integral_vT;也可以使用requires更加灵活地定义concept例如下面的例子要求T类型拥有一个名字叫做print的方法另外需要拥有一个toString方法并且返回值是string类型。
http://www.rkmt.cn/news/1400383.html

相关文章:

  • Windows窗口置顶终极指南:5分钟掌握AlwaysOnTop提升工作效率
  • 免费QQ音乐格式转换终极指南:如何用QMCDecode解锁加密音频文件
  • NBTExplorer:Minecraft数据编辑的终极图形化解决方案
  • 番茄小说下载器:从网络小说到个人图书馆的一站式解决方案
  • 【AI Agent物联网应用落地指南】:20年专家亲授5大避坑法则与3个已验证商业场景
  • HoRain云--Claude Code 记忆系统(Memory)
  • 2607.从重复劳作到高效采集:二手车数据抓取的技术落地与功能实现
  • 构建本地语音控制AI智能体:从语音识别到安全文件操作的全栈实践
  • Linux系统常用的目录和文件基础操作(一)
  • 2608.百度故事自动发布效率低?这款自动化工具从底层逻辑解决创作者核心痛点 | 技术实操
  • 8天构建AI自动生成PR描述工具:从零到一的技术实战复盘
  • 从37欧元账单到3.5欧元:Serverless架构重构实战与云成本优化指南
  • XUnity.AutoTranslator终极指南:Unity游戏实时翻译与多语言支持解决方案
  • Codex Chrome 插件
  • C语言变量
  • LaTeX列表排版进阶:用enumitem宏包5分钟搞定自定义缩进与符号
  • 别再只盯着BIOS了!聊聊ACPI这个‘隐形管家’如何管好你电脑的睡眠与唤醒
  • 别只当连线工具!用AXI Interconnect IP核给你的FPGA设计做‘深度体检’与性能调优
  • 5步彻底解决TranslucentTB安装错误:Windows任务栏透明化工具安装指南
  • NVIDIA Profile Inspector:3步解锁显卡隐藏性能,告别游戏卡顿
  • 逆向工程解密:RePKG如何破解Wallpaper Engine的二进制堡垒
  • j基于深度学习的人体行为识别 摔倒识别 跌倒检测 站立识别
  • Seraphine:英雄联盟玩家的10大智能助手功能,一键提升游戏体验
  • 70-Java HashSet 类
  • 2026济南商用空调维修推荐,腾扬制冷靠谱保障一站式服务性价比高 - myqiye
  • Ubuntu 22.04 LTS下屏幕分辨率显示‘Unknown display’?用xrandr和xorg.conf两步搞定
  • 碧蓝航线全自动脚本:3分钟快速部署,彻底解放你的游戏时间
  • 那个天天准点下班的同事,原来偷偷在用 FastDDD
  • Page Assist终极指南:在浏览器中安全使用本地AI的完整教程
  • 混合视觉Transformer硬件加速:挑战与优化方案