10

コピー不可および割り当て不可のvector::emplaceオブジェクトをデフォルトで構築し、新しく作成されたオブジェクトへのイテレーターを使用して、オブジェクトで特定のメソッドを使用したいと考えています。クラスのパラメーター化されたコンストラクターはなく、デフォルトのコンストラクターだけであることに注意してください。簡単な例は次のとおりです。

#include <iostream>
#include <vector>
using namespace std;

class Test {
public:
    Test() {}
private:
    Test(const Test&) = delete;             // To make clas un-copyable.
    Test& operator=(const Test&) = delete;

    int a_;
};

int main() {
    vector<Test> test_vec;
    test_vec.emplace_back();     // <---- fails

    return 0;
}

vector::emplace()新しいオブジェクトを構築しますが、デフォルト以外のコンストラクタへの引数が必要です。vector::emplace_back()ベクトルの最後に構築されます。

デフォルトの構築で定置する方法はありますか。std::piecewise_constructおそらくマップの場合と同様に、区分的な構築またはデフォルトの転送を使用する方法はありますか? たとえば、マップの場合、次を使用できます。

std::map<int,Test> obj_map;
int val = 10;
obj_map.emplace(std::piecewise_construct,
                std::forward_as_tuple(val),
                std::forward_as_tuple());

ベクトルに似たものはありますか?

4

3 に答える 3

9

vector::emplace_back()ベクトルの最後に構築されますが、引数も必要です。

パラメータ パックは空にすることができます。したがって、可変個引数テンプレートは引数emplace_backなしで呼び出すことができます。いえ

vector<VeryLimitedClass> vec;
vec.emplace_back();

タイプのオブジェクトVeryLimitedClassをそのデフォルト コンストラクターを介して初期化し、それを の後ろに「配置」する有効なコードですvec

于 2014-11-21T18:45:52.700 に答える
6

コメントで @dyp と @Casey が指摘したように、「ユーザー宣言のコピー コンストラクターがデフォルトの移動コンストラクターの生成を抑制する」ため、クラスも移動できないstd::emplaceため、Test クラスのベクトルでは機能しません (@Casey)。

ここで使用emplaceするには、クラスが可動である必要があります。move コンストラクターを明示的に定義 (およびデフォルト設定) することで、これを行うことができます。

public:
    Test(Test&& other) = default;
    Test& operator=(Test&& other) = default;

これにより、 「移動操作を宣言するとコピーの暗黙的な生成が抑制されるため」、暗黙的にクラスがコピー不可になります。(@ケーシー)

これでstd::emplace_back()、 を使用vector::back()して、新しく作成されたオブジェクトのメソッドを呼び出すことができます。

于 2014-11-21T19:45:31.407 に答える
0

の場合map、簡単:

std::map<int, Object> obj_map;
obj_map[10]; // default-constructs an object with key 10

そうでなければ、あなたが持っているものも機能します:

obj_map.emplace(std::piecewise_construct,
                std::forward_as_tuple(10),
                std::forward_as_tuple(args, to, construct, with));

[編集] に相当するものvectorは次のemplace_backとおりです。

obj_vector.emplace_back(); // default construct
obj_vector.emplace_back(args, to, std::move(construct), with); // forward these
于 2014-11-21T18:31:28.267 に答える