CRTP std :: is_default_constructible无法正常工作 [英] CRTP std::is_default_constructible not working as expected

查看:120
本文介绍了CRTP std :: is_default_constructible无法正常工作的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

template <class T>
class Base {
     static_assert(!std::is_default_constructible<T>::value,
                   "T must not be default constructible");
};

struct X1 : Base<X1> {};
struct X2 : Base<X2> {
   X2() = default;
};
struct X3 : Base<X3> {
   X3() {};
};
struct X4 : Base<X4> {
   X4() : Base{} {};
};

struct Y1 {};

int main() {
    // all compile. They shouldn't
    X1 x1; X2 x2; X3 x3; X4 x4; 
    // all compile. They shouldn't:
    Base<X1> bx1; Base<X2> bx2; Base<X3> bx3; Base<X4> bx4;  

    Base<Y1> by1; // static assert fires. This is the expected behavior
}

对于任何X类,都不会触发类级别的static_assert.但是加入Y(不会派生Base)

The static_assert at class level doesn't fire for any of the X classes. But kicks in for Y (which doesn't derive Base)

如果将static_assert移到Base

如果T源自Base,则is_default_constructible<T>在类级别始终为false的原因是什么?

What is the reason that is_default_constructible<T> is always false at class level if T derives from Base?

Idone

推荐答案

X1的继承列表中实例化Base<X1>时,X1是不完整的类型.这意味着X1在检查类作用域static_assert时不是默认可构造的.

When Base<X1> is instantiated in the inheritance list of X1, X1 is an incomplete type. This means that X1 is not default-constructible when the class-scope static_assert is checked.

Base的构造函数仅在使用时实例化,此时,X1现在是完整类型,并且是默认可构造的.这就是为什么static_assert在构造函数内部而不是在类范围内触发的原因.

The constructor for Base is only instantiated upon use, at which point X1 is now a complete type and is default-constructible. This is why the static_assert fires when inside the constructor, but not at class-scope.

这篇关于CRTP std :: is_default_constructible无法正常工作的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆