为什么海湾合作委员会在实施is_nothrow_constructible时需要static_cast?

Why is static_cast needed in the gcc's implementation of is_nothrow_constructible?

本文关键字:constructible nothrow cast static is 委员会 为什么海      更新时间:2023-10-16

取自 GCC 的实现type_traits为什么这里需要static_cast

template <typename _Tp, typename... _Args>
struct __is_nt_constructible_impl
: public integral_constant<bool, noexcept(_Tp(declval<_Args>()...))> {};
template <typename _Tp, typename _Arg>
struct __is_nt_constructible_impl<_Tp, _Arg>
: public integral_constant<bool,
// Why is `static_cast` needed here?
noexcept(static_cast<_Tp>(declval<_Arg>()))> {};

如果发明的变量声明,则类型可以从参数列表中构造 nothrow

T t(declval<Args>()...);

将格式良好,并且已知不会引发异常。在复数参数的情况下,这等价于类型转换表达式的良好格式和 nothrow (模 noexcept 可破坏性,参见 LWG 2116(

T(declval<Args>()...)

然而,在单参数的情况下,表达式T(declval<Args>())被视为一个强制转换表达式,它可以调用const_castreinterpret_cast;显式使用static_cast恢复了声明形式的等价性。

作为一个具体示例,请考虑以下类型:

struct D;
struct B { operator D&&() const; };
struct D : B {};

在这里,从B constD&&static_cast必须使用转换运算符,但强制转换表达式可以绕过转换运算符,因此除外。因此,省略static_cast会给is_nothrow_constructible<D&&, B const>带来错误的结果。