Выделить больше памяти для динамически выделяемого массива

Мой алгоритм C++ получает данные с неизвестным размером (он обнаруживает частицы на изображении одну за другой, и я не могу знать, сколько частиц будет обнаружено до того, как этот алгоритм завершит свою работу). Итак, сначала я хочу выделить, скажем, массив из 10 000 элементов, а в процессе обработки, при необходимости, несколько раз выделить еще 10 000 элементов.

Вот что я пробовал, это не работает:

#include <iostream>
using namespace std;
int main(){
    int n = 3;
    int m = 3;
    float *a = new float[3];
    a[0] = 0;
    a[1] = 1;
    a[2] = 2;
    float *b = a + 2;
    b = new float[3];
    b[0] = 4;
    b[1] = 5;
    cout << a[3] << endl;
} 

В итоге получил минус бесконечность. Конечно, я могу справиться с этим в разных массивах, могу один раз выделить огромное количество памяти. Мне нужно передать в функцию полный массив обнаруженных данных после, поэтому в результате я хочу иметь один большой массив.

Но все же, есть ли способ увеличить размер вашего динамически выделяемого пути? В примере с игрушкой я хочу увеличить количество элементов в массиве a на 3, чтобы в нем было 6 элементов.

В Матлабе это абсолютно возможно. Что насчет С++?

Спасибо


person Mikhail Genkin    schedule 12.03.2015    source источник
comment
Вам нужен динамический массив. С++ дает вам std::vector для этой цели - вам не нужно беспокоиться о выделении памяти.   -  person Charles Salvia    schedule 12.03.2015


Ответы (3)


Нет, вы не можете увеличить размер массива. Если вы хотите использовать массив, вам придется выделить новый блок, достаточно большой для всего нового массива, и скопировать существующие элементы перед удалением старого массива. Или вы можете использовать более сложную структуру данных, которая не хранит свои элементы непрерывно.

К счастью, в стандартной библиотеке есть контейнеры для автоматической обработки; включая vector, массив с изменяемым размером.

std::vector<float> a(3);
a[0] = 0;
a[1] = 1;
a[2] = 2;

// you can resize it by specifying a new size
a.resize(4);
a[3] = 3;

// or by appending new elements
a.push_back(4);
person Mike Seymour    schedule 12.03.2015
comment
Спасибо! Так что да, векторный класс кажется самым простым решением - person Mikhail Genkin; 12.03.2015

Вам следует просто использовать std::vector вместо необработанных массивов. Он реализован для эффективного роста. Вы можете изменить его размер с помощью resize, добавить к нему push_back или вставьте диапазон (или другие вещи) с помощью insert, чтобы расширить его.

Изменение размера выделенного вручную массива в C++ невозможно. Использование std::vector поверх необработанных массивов в целом является хорошей идеей, даже если размер не меняется. Некоторыми аргументами являются автоматизированное управление памятью с защитой от утечек, дополнительная защита от исключений, а также vector, знающий свой собственный размер.

person Baum mit Augen    schedule 12.03.2015

Вы должны использовать vector, а затем resize, когда это необходимо, или позволить ему расти само по себе.

Когда вы делаете:

float *b = a + 2;
b = new float[3];

выделенная память не будет выделена непрерывно с первым выделением, даже если вы ранее установили указатель на конец (он все равно будет перезаписан). Поэтому при обращении к a[3] вы выходите за пределы.

person Eric Fortin    schedule 12.03.2015