C++20标准下requires子句中b<[]{ return true; }()表达式是否合规?
问题:requires子句中使用
b<[]{ return true; }()是否符合C++20标准? 将表达式b<[]{ return true; }()置于requires子句中是否符合C++20标准?目前GCC判定该表达式存在错误并拒绝编译,而MSVC与Clang均接受该代码。
代码示例
template<bool B> inline constexpr bool b = B; static_assert(requires { b<[]{ return true; }()>; });
GCC错误信息
<source>:3:15: error: static assertion failed 3 | static_assert(requires { b<[]{ return true; }()>; }); | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ <source>:3:15: note: constraints not satisfied <source>:3:26: note: the required expression 'b<<expression error> >' is invalid, because 3 | static_assert(requires { b<[]{ return true; }()>; }); | ^~~~~~~~~~~~~~~~~~~~~~~
回答
这段代码完全符合C++20标准,GCC的报错属于编译器实现bug。
C++20允许在模板实参位置使用立即调用的lambda表达式:[]{ return true; }()会被立即求值为true,作为布尔类型的模板实参传递给b模板变量。而requires子句的表达式上下文属于潜在求值场景,标准并未禁止在此处使用这类立即调用的lambda作为模板实参。
MSVC和Clang的行为是符合标准的,GCC在处理requires子句内的这种模板实参求值逻辑时存在兼容性问题,后续版本大概率会修复该bug。
内容的提问来源于stack exchange,提问作者303
相关产品推荐
相关产品推荐

