Операторы динамического распределения памяти: new(), delete(); malloc(), free().
В языке С++ предусмотрены два оператора динамического распределения памяти: new и delete. Эти операторы выделяют и освобождают память в ходе выполнения программы. Динамическое распределение памяти представляет собой важную часть практически всех реальных программ. В языке С++ есть альтернативный способ динамического распределения памяти, основанный на функциях malloc() и free(). Они сохранены для того, чтобы достичь совместимости с языком С. Однако в программах на языке С++ следует применять операторы new и delete, поскольку они имеют ряд важных преимуществ: во-первых, оператор new автоматически выделяет количество памяти, необходимое объекту указанного типа (оператор Операция sizeof теперь применять не следует), во-вторых, оператор new автоматически возвращает указатель заданного типа. Также операторы new и delete можно перегружать, что позволяет создавать настраиваемые системы для выделения динамической памяти.
Оператор new выделяет область памяти и возвращает указатель на ее первую ячейку. Оператор delete освобождает память, выделенную ранее с помощью оператора new.
/* * File: * Author: darkfire * * Created on September 15, 2010, 6:32 PM */ #include <iostream> #include <ctime> #include <stdlib.h> using namespace std; const int SIZE = 7; int main () { srand(time(NULL)); int *parr = new int [SIZE]; // Определили указатель. Выделили память для массива. int *parr0 = parr; //сохранили для дальнейшего использования адресс массива. for (int i=0;i<SIZE-1;i++){ *parr=rand()%100; cout<<*parr<<"\n"; parr++; } parr = parr0; for (int i=0;i<SIZE-1;i++){ cout<<*parr<<"\n"; parr++; } parr = parr0;/* если указателю не присвоить адресс первого элемента массива * оператор делете будет выводить ошибку. */ delete [] parr; }
Многомерный массив в C по своей сути одномерен. Операции new и delete позволяют создавать и удалять динамические массивы, поддерживая при этом иллюзию произвольной размерности. Деятельность по организации динамического массива требует дополнительного внимания, которое окупается важным преимуществом: характеристики массива (операнды операции new) могут не быть константными выражениями. Это позволяет создавать многомерные динамические массивы произвольной конфигурации.
Следующий пример иллюстрирует работу с динамическими массивами.
#include <iostream> using namespace std; void main() { int i, j; // Переменные для описания характеристик массивов. int m1 = 5, m2 = 5; /* Организация двумерного динамического массива производится в два этапа. Сначала создаётся одномерный массив указателей, а затем каждому элементу этого массива присваивается адрес одномерного массива. Для характеристик размеров массивов не требуется константных выражений. */ int **pArr = new int*[m1]; for (i = 0; i < m1; i++) pArr[i] = new int[m2]; pArr[3][3] = 100; cout << pArr[3][3] << "\n"; //Последовательное уничтожение двумерного массива… for (i = 0; i < m1; i++) delete[]pArr[i]; delete[]pArr; }
Например, мы хотим увеличить размер уже существующего динамического массива на 1.
Сначала создаётся одномерный массив указателей, а затем каждому элементу этого массива присваивается адрес одномерного массива. При этом размер (количество элементов) каждого нового массива на единицу меньше размера предыдущего. Включённая в квадратные скобки переменная, которая является операндом операции new, позволяет легко сделать это.
#include <iostream> using namespace std; void main() { int i, j; // Переменные для описания характеристик массивов. int m1 = 5, wm = 5; int **pXArr = new int*[m1]; for (i = 0; i < m1; i++, wm--) pXArr[i] = new int[m1]; //Заполнение массива нулями и показ его на экран for (i = m1 - 1; i >= 0; i--, wm++) { for (j = 0; j < wm; j++){ pXArr[i][j]=0; cout<<pXArr[i][j]<<"\t"; } cout<<"\n\n"; } //Последовательное уничтожение двумерного массива треугольной конфигурации… for (i = 0; i < m1; i++) delete[]pXArr[i]; delete[]pXArr; }
Создание и уничтожение трёхмерного массива требует дополнительной итерации. Однако здесь также нет ничего принципиально нового.
#include <iostream> using namespace std; void main() { int i, j; // Переменные для описания характеристик массивов. int m1 = 5, m2 = 5, m3 = 2; // указатель на указатель на указатель :) int ***ppArr; // Создание массива ppArr = new int**[m1]; for (i = 0; i <m1; i++) ppArr[i] = new int*[m2]; for (i = 0; i < m1; i++) for (j = 0; j < m2; j++) ppArr[i][j] = new int[m3]; ppArr[1][2][3] = 750; cout << ppArr[1][2][3] << "\n"; // Удаление в последовательности, обратной созданию for (i = 0; i < m1; i++) for (j = 0; j < m2; j++) delete[]ppArr[i][j]; for (i = 0; i < m1; i++) delete[]ppArr[i]; delete[] ppArr; }