Wenn Sie C++11 verwenden und die Elemente verschieben möchten, anstatt sie nur zu kopieren, können Sie std::move_iterator
zusammen mit der Beilage (oder Kopie):
#include <vector>
#include <iostream>
#include <iterator>
int main(int argc, char** argv) {
std::vector<int> dest{1,2,3,4,5};
std::vector<int> src{6,7,8,9,10};
// Move elements from src to dest.
// src is left in undefined but safe-to-destruct state.
dest.insert(
dest.end(),
std::make_move_iterator(src.begin()),
std::make_move_iterator(src.end())
);
// Print out concatenated vector.
std::copy(
dest.begin(),
dest.end(),
std::ostream_iterator<int>(std::cout, "\n")
);
return 0;
}
Für das Beispiel mit den Ints ist dies nicht effizienter, da das Verschieben von Ints nicht effizienter ist als das Kopieren, aber für eine Datenstruktur mit optimierten Verschiebungen kann es das Kopieren unnötiger Zustände vermeiden:
#include <vector>
#include <iostream>
#include <iterator>
int main(int argc, char** argv) {
std::vector<std::vector<int>> dest{{1,2,3,4,5}, {3,4}};
std::vector<std::vector<int>> src{{6,7,8,9,10}};
// Move elements from src to dest.
// src is left in undefined but safe-to-destruct state.
dest.insert(
dest.end(),
std::make_move_iterator(src.begin()),
std::make_move_iterator(src.end())
);
return 0;
}
Nach dem Verschieben bleibt das Element von src in einem undefinierten, aber zerstörungssicheren Zustand, und seine früheren Elemente wurden am Ende direkt in das neue Element von dest übertragen.
10 Stimmen
Die gegebenen Antworten sind nicht wirklich zusammenhängend. Sie fügen eine Kopie an. Es könnte (aus Gründen der Effizienz) sinnvoll sein, eine std::vector concatenate-Methode zu erstellen, allerdings würde dies eine ausgeklügelte gemeinsame Nutzung der Verwaltung der Knoten erfordern, und das ist wahrscheinlich der Grund, warum dies noch nicht geschehen ist.
16 Stimmen
@FauChristian: Nein, unter Effizienzgesichtspunkten kann es keinen Nutzen geben. Der Vektorspeicher muss kontinuierlich sein, also ist das, was Sie vorschlagen, unmöglich. Wenn Sie "eine ausgeklügelte gemeinsame Nutzung der Verwaltung der Knoten" wollten und die Vektorklasse auf diese Weise ändern würden, würden Sie bei einer Deque landen. Selbst dann ist es sehr schwierig, den Speicher in der vorgeschlagenen Weise wiederzuverwenden, auch wenn es allmählich ein wenig praktikabler wäre. Ich glaube nicht, dass es derzeit implementiert ist. Die Hauptsache ist, dass in einem solchen Sharing von Management-Knoten (eine deque) der Endknoten teilweise leer sein könnte.
18 Stimmen
Bin ich der Einzige, der sich fragt, warum dies nicht als
a + b
oa.concat(b)
in der Standardbibliothek? Vielleicht wäre die Standardimplementierung suboptimal, aber nicht jede Array-Verkettung muss mikro-optimiert sein58 Stimmen
Jahre der Entwicklung, das fortschrittlichste Operator-Overloading aller Mainstream-Sprachen, ein Templating-System, das die Komplexität der Sprache verdoppelt, und dennoch lautet die Antwort nicht v = v1 + v2;
7 Stimmen
Ich vermute, dass die STL die Sprache nicht überspezifizieren wollte, für den Fall, dass der Operator etwas anderes tun sollte, z. B. Kraftvektoren in einem Physikmodell hinzufügen. In diesem Fall könnten Sie überladen wollen
forceVector1 + forceVector2
um in klarem, prägnantem Code punktweise zu addieren.3 Stimmen
@Spike0xff, v = v1 + v2 hat in der Mathematik eine Bedeutung, die nichts mit Verkettung zu tun hat. Es hat auch einige Anforderungen, um berechenbar zu sein. Ich würde eher eine Append-Methode vorschlagen (eine Abkürzung dessen, was man mit
insert
) oder eine Push-Back-Überlastung.