Zmiana rozmiaru w C ++ jest niewygodna ze względu na potencjalną potrzebę wywoływania konstruktorów i destruktorów.
Nie sądzę, aby istniał podstawowy powód, dla którego w C ++ nie można było mieć resize[]
operatoranew[]
a delete[]
to zrobiło coś podobnego do tego:
newbuf = new Type[newsize];
std::copy_n(oldbuf, std::min(oldsize, newsize), newbuf);
delete[] oldbuf;
return newbuf;
Oczywiście oldsize
zostałby pobrany z tajnego miejsca, w którym się znajduje delete[]
, i Type
pochodziłby z typu operandu. resize[]
nie powiedzie się, gdy Typ nie jest kopiowalny - co jest poprawne, ponieważ takich obiektów po prostu nie można przenieść. Na koniec powyższy kod domyślnie konstruuje obiekty przed ich przypisaniem, czego nie chcesz, ponieważ jest to rzeczywiste zachowanie.
Możliwa jest optymalizacja, w której newsize <= oldsize
polegająca na wywołaniu destruktorów obiektów „poza końcem” nowo utworzonej tablicy i nic więcej. Standard musiałby zdefiniować, czy ta optymalizacja jest wymagana (jak w przypadku resize()
wektora), dozwolona, ale nieokreślona, dozwolona, ale zależna od implementacji, czy zabroniona.
Pytanie, które powinieneś sobie wtedy zadać, brzmi: „czy rzeczywiście warto to zapewnić, biorąc pod uwagę, że vector
również to robi, i jest zaprojektowany specjalnie w celu zapewnienia kontenera z możliwością zmiany rozmiaru (ciągłej pamięci - to wymaganie zostało pominięte w C ++ 98, ale poprawione w C ++ 03), które są lepsze niż tablice ze sposobami robienia rzeczy w C ++? ”
Myślę, że powszechnie uważa się, że odpowiedź brzmi „nie”. Jeśli chcesz robić bufory o zmiennym rozmiarze na sposób C, użyj malloc / free / realloc
, które są dostępne w C ++. Jeśli chcesz tworzyć bufory o zmiennym rozmiarze w sposób C ++, użyj wektora (lub deque
, jeśli w rzeczywistości nie potrzebujesz ciągłego przechowywania). Nie próbuj mieszać tych dwóch, używając new[]
dla surowych buforów, chyba że implementujesz kontener podobny do wektora.