支持空初始值设定项列表的高效对象构造

Efficient object construction supporting empty initializer lists

本文关键字:列表 高效 对象 支持      更新时间:2023-10-16

我有一个这样的类,除了有多个成员:

struct S {
    S( S&& s ) : member( std::move( s.member ) ) {}
    std::vector< int > member;
};

我基本上想要像这样对它进行聚合初始化:

S s{ {} };

但由于自定义构造函数,这似乎是不可能的,所以我想使用构造函数参数来模拟它:

struct S {
    S( S&& s ) : member( std::move( s.member ) ) {}
    S( std::vector< int >&& vec ) : member( std::move( vec ) ) {}
    S( const std::vector< int >& vec ) : member( vec ) {}
    std::vector< int > member;
};

这看起来有很多冗余,只是为了尽可能移动并以其他方式复制,尤其是由于排列数量爆炸而具有更多成员的情况下。我想我想要完美的转发?

struct S {
    template< typename V >
    S( V&& vec ) : member( std::forward< V >( vec ) ) {}
    S( S&& s ) : member( std::move( s.member ) ) {}
    std::vector< int > member;
};

但是现在我不能像这样用空的初始值设定项列表调用它:

S s( {} );

因为无法推断初始值设定项列表参数类型。有没有不需要我写的解决方案

S s( std::vector<int>{} );

目前尚不清楚为什么添加默认构造函数不适合您,只需允许S s{}

struct S {
    S() = default;
    S( S&& s ) = default;
    std::vector< int > member;
};

如果这不合适,您有多种选择。最明显的是摆脱你的移动构造函数,所以类是一个聚合。无论如何,您展示的移动构造函数毫无意义,它不会做隐式定义的构造函数不会做的任何操作。

struct S {
    std::vector< int > member;
};

下一个选项是添加初始值设定项列表构造函数:

struct S {
    S() = default;
    S( S&& s ) = default;
    S(std::initializer_list<int> il) : member(il) { }
    std::vector< int > member;
};

这将允许您将大括号的初始化列表传递给vector成员。

如果您只希望能够将空的初始值设定项列表传递给向量,另一种选择是重载构造函数,以便将某些内容传递给向量是可选的(但您仍然可以为其他成员传递参数)。这意味着您只需省略向量的无意义的{}参数,并让它默认构造。