2014-07-03 12 views
5

ich habe ein std::vector<std::vector<double>> und möchte einige Elemente am Ende, um es hinzuzufügen und so war mein Versuch:Emplacement eines Vektors mit Initialisiererliste

std::vector<std::vector<double> > vec; 
vec.emplace_back({0,0}); 

aber nicht kompiliert, während das Folgende tun:

std::vector<double> vector({0,0}); 

Warum kann emplace_back nicht das Element an dieser Position konstruieren? Oder was mache ich falsch?

Danke für Ihre Hilfe.

Antwort

7

Der Vorlagenabzug kann nicht vermuten, dass die in Klammern eingeschlossene Initialisierungsliste ein Vektor sein sollte. Sie müssen in der expliziten:

vec.emplace_back(std::vector<double>{0.,0.}); 
+0

Danke, aber ich habe noch eine Frage zu diesem: Warum ist es für das zweite Beispiel arbeiten? Da der Compiler ähnliche Informationen über den Typ hat (emplace_back erwartet, Argumente für einen Konstruktor von std :: vector zu bekommen, und so ist das zweite Beispiel) – m47h

+0

Weil im zweiten Beispiel Sie den Konstruktor von Vektor aufrufen, der die Initialisiererliste behandeln kann direkt. – marli

+3

So effektiv Sie nicht platzieren, sondern nur ein bereits konstruiertes Element schieben, anstatt den Vektor an Ort und Stelle zu konstruieren. –

6

Die vorherigen Antwort erwähnt Sie den Code bekommen könnte zu kompilieren, wenn Sie den Vektor in Linie konstruieren und einzulagern. Das bedeutet jedoch, dass Sie den move-Konstruktor für einen temporären Vektor aufrufen, was bedeutet, dass Sie den Vektor nicht direkt erstellen, obwohl dies der ganze Grund für die Verwendung von emplace_back anstelle von push_back ist.

Stattdessen sollten Sie werfen die Initialisiererliste zu einem initializer_list, etwa so:

#include <vector> 
#include <initializer_list> 

int main() 
{ 
    std::vector<std::vector<int>> vec; 
    vec.emplace_back((std::initializer_list<int>){1,2}); 
} 
+0

Es würde tatsächlich den Move-Konstruktor aufrufen, nicht den Copy-Konstruktor. – Arcinde

+0

Guter Fang. Bearbeitete meine Antwort. –

+0

Warum verwenden Sie die alte C-Cast-Syntax '(std :: initializer_list ) {1,2}' hier anstelle der Konstruktorsyntax 'std :: initializer_list ({1,2})'? – Peter