Ich versuche, eine Kopie eines vorhandenen vector
-Elements einzufügen, um es zu verdoppeln. Der folgende Code funktionierte in früheren Versionen, scheitert jedoch in Visual Studio 2010.
#include
#include
using namespace std;
int main(int argc, char* argv[])
{
vector test;
test.push_back(1);
test.push_back(2);
test.insert(test.begin(), test[0]);
cout << test[0] << " " << test[1] << " " << test[2] << endl;
return 0;
}
Die Ausgabe lautet -17891602 1 2
, erwartet wird 1 1 2
.
Ich habe herausgefunden, warum das passiert - der Vektor wird neu zugeordnet und die Referenz wird ungültig, bevor sie an die Einfügestelle kopiert wird. Das ältere Visual Studio führt die Dinge offenbar in einer anderen Reihenfolge aus, was beweist, dass ein mögliches Ergebnis eines undefinierten Verhaltens korrektes Funktionieren ist und auch beweist, dass man sich darauf nie verlassen sollte.
Ich habe zwei verschiedene Möglichkeiten gefunden, dieses Problem zu beheben. Eine besteht darin, reserve
zu verwenden, um sicherzustellen, dass keine Neuordnung stattfindet:
test.reserve(test.size() + 1);
test.insert(test.begin(), test[0]);
Die andere besteht darin, eine Kopie aus der Referenz zu erstellen, sodass keine Abhängigkeit von der Gültigkeit der Referenz besteht:
template
T make_copy(const T & original)
{
return original;
}
test.insert(test.begin(), make_copy(test[0]));
Obwohl beide Lösungen funktionieren, fühlt sich keine wie eine natürliche Lösung an. Gibt es etwas, das ich übersehe?