Oto fragment kodu, że szukałem w:Jak iteratory aktualizacji po wektora realokacji
vector<int> iv = {1,2,3,4,5,6,7,8,9,10};
auto iter = iv.begin(), mid = iv.begin() + iv.size()/2;
for(int count = 100; count; --count) {
iter = iv.insert(iter, - 1);
cout << "capacity = " << iv.capacity() << "*mid = " << *mid << endl;
}
zgodnie zasad unieważniania, iterator:
Vector: wszystkie iteratory oraz odniesienia przed punktem wstawiania są nienaruszone, chyba że nowy rozmiar kontenera jest większy niż poprzednia pojemność (w tym przypadku wszystkie iteratory i odwołania są unieważniane) [23.2.4.3/1] Iterator invalidation rules
Rozumiem, że ponieważ ponownie przypisuję wartość "iter" w każdej wstawce operacja, być może jestem w stanie utrzymać jego ważność (popraw mnie, jeśli się mylę). Jednak iterator "w połowie" zachowuje ważność w tym przypadku, nawet jeśli nie manipuluję nim w pętli, a także gdy zmienia się pojemność wektora.
W jaki sposób "w połowie" jest w stanie zaktualizować się po realokacji?
Aby dowiedzieć się, czy w połowie zmienia się w ogóle lub nie, zmieniłem linii 4 w kodzie:
iv.insert(iter, -1); // Did not assign it back to iter.
Drukowanie wyników dereferencing wartość w połowie sugeruje zmianę i być może również, że ITER jest unieważniony . (Ponownie, popraw mnie, jeśli się mylę).
Dlaczego uważasz, że "średni" jest nadal ważny? Przypuszczam, że to dlatego, że (* w połowie) drukuje "6", ale jest to tylko zwisający iterator wskazujący gdzieś w wolnej pamięci, która nie zmieniła poprzedniej wartości. Jeśli uruchomisz valgrind, dostaniesz dużo nieprawidłowego dostępu do pamięci. – kukyakya