可变参数构造函数应该隐藏隐式生成的构造函数吗? [英] Are variadic constructors supposed to hide the implicitly generated ones?

查看:159
本文介绍了可变参数构造函数应该隐藏隐式生成的构造函数吗?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

可变参数构造函数应该隐藏隐式生成的构造函数,即默认构造函数和复制构造函数?

Are variadic constructors supposed to hide the implicitly generated ones, i.e. the default constructor and the copy constructor?

struct Foo
{
    template<typename... Args> Foo(Args&&... x)
    {
        std::cout << "inside the variadic constructor\n";
    }
};

int main()
{
    Foo a;
    Foo b(a);
}

不知何故,我希望在读取这个回答,但是它在里面打印可变参数构造函数在g ++上两次4.5.5 :(这是正确的行为吗?

Somehow I was expecting this to print nothing after reading this answer, but it prints inside the variadic constructor twice on g++ 4.5.0 :( Is this behavior correct?

没有可变参数模板时发生:

It also happens without variadic templates:

struct Foo
{
    Foo()
    {
        std::cout << "inside the nullary constructor\n";
    }

    template<typename A> Foo(A&& x)
    {
        std::cout << "inside the unary constructor\n";
    }
};

int main()
{
    Foo a;
    Foo b(a);
}

推荐答案

隐含声明的拷贝构造函数的声明实际上不是被抑制的。

Declaration of the implicitly declared copy constructor is not, in fact, being suppressed. It's just not being called due to the rules of overload resolution.

隐式声明的拷贝构造函数具有 Foo(const Foo&)。这个的重要部分是它需要一个const引用。您的构造函数模板采用非const引用。

The implicitly declared copy constructor has the form Foo(const Foo&). The important part of this is that it takes a const reference. Your constructor template takes a non-const reference.

a 不是const,声明的构造函数模板比​​隐式声明的拷贝构造函数优先。要调用隐式声明的复制构造函数,可以使 a const:

a is not const, so the non-const user-declared constructor template is preferred over the implicitly-declared copy constructor. To call the implicitly-declared copy constructor, you can make a const:

const Foo a;
Foo b(a);

或者您可以使用 static_cast const引用 a

or you can use static_cast to obtain a const reference to a:

Foo a;
Foo b(static_cast<const Foo&>(a));

描述这种情况的重载解析规则主要发现在C ++的§13.3.3.2/ + 0x FCD。这种特殊情况,包括左值和右值引用的组合,在第303页的各种示例中进行了描述。

The overload resolution rules that describe this are found mostly in §13.3.3.2/3 of the C++0x FCD. This particular scenario, with a combination of lvalue and rvalue references, is sort of described by the various examples on page 303.

可变参数构造函数模板将抑制隐式声明的默认构造函数,因为可变参数构造函数模板是用户声明的,并且仅当没有用户声明的构造函数(C ++ 0x FCD§12.1/ 5)时才提供隐式声明的默认构造函数:

A variadic constructor template will suppress the implicitly declared default constructor because a variadic constructor template is user-declared and the implicitly declared default constructor is only provided if there are no user-declared constructors (C++0x FCD §12.1/5):


如果类 X 没有用户声明的构造函数,没有参数隐式声明为默认。

If there is no user-declared constructor for class X, a constructor having no parameters is implicitly declared as defaulted.

可变参数构造函数模板不会抑制隐式声明的拷贝构造函数,因为只有一个非模板构造函数可以是复制构造函数(C ++ 0x FCD§12.8/ 2,3和8):

A variadic constructor template will not suppress the implicitly declared copy constructor because only a non-template constructor can be a copy constructor (C++0x FCD §12.8/2, 3, and 8):


如果第一个参数是 X& const X& ; volatile X& const volatile X& 参数或其他所有参数都有默认参数。

A non-template constructor for class X is a copy constructor if its first parameter is of type X&, const X&, volatile X& or const volatile X&, and either there are no other parameters or else all other parameters have default arguments.

X 的非模板构造函数是一个move构造函数如果其第一个参数是 X&& const X&&& volatile X&& const volatile X&&& ,并且没有其他参数或所有其他参数都有默认参数。

A non-template constructor for class X is a move constructor if its first parameter is of type X&&, const X&&, volatile X&&, or const volatile X&&, and either there are no other parameters or else all other parameters have default arguments.

如果类定义没有显式声明一个复制构造函数,并且没有用户声明的move构造函数,那么一个复制构造函数被隐式声明为默认。

If the class definition does not explicitly declare a copy constructor and there is no user-declared move constructor, a copy constructor is implicitly declared as defaulted.

这篇关于可变参数构造函数应该隐藏隐式生成的构造函数吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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