if constexpr和require-expression用于临时概念检查 [英] if constexpr and requires-expression for ad-hoc concepts checking
问题描述
比方说,假设C ++ 17的 if constexpr
和Concepts TS(例如,在最新的gcc版本中),我们想检查一下模板函数具有嵌套类型:
Let's say, given C++17's if constexpr
and Concepts TS (for instance, in recent gcc versions), we'd like to check if a type in a template function has a nested type:
#include <iostream>
struct Foo { using Bar = int; };
template<typename T>
void doSmth(T)
{
if constexpr (requires { typename T::Bar; })
std::cout << "has nested! " << typename T::Bar {} << std::endl;
else
std::cout << "no nested!" << std::endl;
}
int main()
{
doSmth(Foo {});
//doSmth(0);
}
关于概念的文档很少,所以我可能弄错了,但是似乎就是这样(实际示例在 Wandbox 上)。
The documentation for concepts is scarce, so I might have got it wrong, but seems like that's it (and the live example is on Wandbox).
现在让我们考虑取消对其他 doSmth
调用的注释时应该发生的情况。可以预期,需求子句将评估为 false
和<$ c的 else
分支,这似乎是合理的$ c>如果使用constexpr 。与此相反,gcc使其成为一个硬错误:
Now let's consider what should happen when uncommenting the other doSmth
call. It seems reasonable to expect that the requires-clause would evaluate to false
, and the else
branch of the if constexpr
will be taken. Contrary to that, gcc makes this a hard error:
prog.cc: In instantiation of 'void doSmth(T) [with T = int]':
prog.cc:17:13: required from here
prog.cc:8:5: error: 'int' is not a class, struct, or union type
if constexpr (requires { typename T::Bar; })
^~
是gcc中的错误,还是预期的行为?
Is that a bug in gcc, or is that the intended behaviour?
推荐答案
概念问题3 (在更多情况下允许 requires-expression s)在六月获得WP资格。从 [expr.prim.req] 的当前外观来看,特别是p6:
Concepts issue 3 ("Allow requires-expressions in more contexts") was given WP status in June. And judging by the current looks of [expr.prim.req], in particular p6:
将模板参数替换为 requires-expression 可能导致无效的形成类型或表达式的需求或违反这些需求的语义约束。在这种情况下, requires-expression 的评估结果为
false
;
The substitution of template arguments into a requires-expression may result in the formation of invalid types or expressions in its requirements or the violation of the semantic constraints of those requirements. In such cases, the requires-expression evaluates to
false
; it does not cause the program to be ill-formed.
我想说您的代码很好,而且GCC尚未实现问题3的解决方法正确。
I'd say your code is fine, and GCC hasn't implemented the resolution of issue 3 properly.
这篇关于if constexpr和require-expression用于临时概念检查的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!