Опубликован: 02.02.2011 | Уровень: для всех | Доступ: свободно
Лекция 25:

Распределение памяти. Динамическое выделение памяти

< Лекция 24 || Лекция 25: 123 || Лекция 26 >

Работа с динамической памятью с помощью библиотечных функций malloc (calloc) и free

Средства для динамического выделения и освобождения памяти описаны в заголовочных файлах malloc.h и stdlib.h стандартной библиотеки (файл malloc.h ).

Функции выделения и освобождения памяти
Функция Прототип и краткое описание
malloc void * malloc (unsigned s); возвращает указатель на начало области (блока) динамической памяти длинной в s байт. При неудачном завершении возвращает значение NULL.
calloc void * calloc (unsigned n, unsigned m); возвращает указатель на начало области (блока) обнуленной динамической памяти, выделенной для размещения n элементов по m байт каждый. При неудачном завершении возвращает значение NULL.
realloc void * realloc (void * bl, unsigned ns); изменяет размер блока ранее выделенной динамической памяти до размера ns байт, bl – адрес начала изменяемого блока. Если bl равен NULL (память не выделялась), то функция выполняется как malloc.
free void * free (void * bl); освобождает ранее выделенный участок (блок) динамической памяти, адрес первого байта которого равен значению bl.

Функции malloc(), calloc() и realloc() динамически выделяют память в соответствии со значениями параметров и возвращают адрес начала выделенного участка памяти. Для универсальности тип возвращаемого значения каждой из этих функций есть void *. Этот указатель можно преобразовать к указателю любого типа с помощью операции явного приведения типа ( тип * ).

Функция free() освобождает память, выделенную перед этим с помощью одной из трех функций malloc(), calloc() или realloc(). Сведения об участке памяти передаются в функцию free() с помощью указателя – параметра типа void *. Преобразование указателя любого типа к типу void * выполняется автоматически, поэтому вместо формального параметра void *bl можно подставить в качестве фактического параметра указатель любого типа без операции явного приведения типов.

Пример 2. Ввести и напечатать в обратном порядке набор вещественных чисел, количество которых заранее не фиксировано, а вводится до начала ввода самих числовых значений.

#include "stdafx.h"
#include <iostream>
using namespace std;
int _tmain(int argc, _TCHAR* argv[]){
  float* t; //Указатель для выделяемого блока памяти 
  int i,n;
  printf("n=");//n - число элементов
  scanf("%d", &n);
  t=(float *)malloc(n*sizeof(float));
  for (i=0; i<n; i++){ //цикл ввода чисел
    printf("x[%d]=",i);
    scanf("%f", &t[i]);
  }
  //цикл печати результатов
  for (i=n-1; i>=0; i--){
    printf("\nx[%d]=%f",i,t[i]);
  }
  free(t); //освобождает память
  system("pause");
  return 0;
}

В программе int n – количество вводимых чисел типа float, float* tуказатель на начало области, выделяемой для размещения n вводимых чисел. Указатель t принимает значение адреса области, выделяемой для n значений типа float. Доступ к участкам памяти выделенной области выполняется с помощью операции индексирования: t[i] и t[i-1]. Оператор free(t); содержит вызов функции, освобождающей выделяемую ранее динамическую память и связанной с указателем t.

Ключевые термины

Динамическая память – это память, выделяемая программе для ее работы за вычетом сегмента данных, стека, в котором размещаются локальные переменные подпрограмм и собственно тела программы.

Динамические переменные – это переменные, определенные в области динамической памяти.

Операция выделения динамической памяти – это выделение достаточного для размещения величины участка динамической памяти.

Операция освобождения динамической памяти – это освобождение участка динамической памяти, выделенного ранее.

Сегмент данных – это непрерывная область памяти, в которой размещаются объявленные в программе переменные.

Функция выделения динамической памяти – это функция выделения памяти в соответствии со значениями параметров, возвращающая адрес начала выделенного участка памяти.

Функция освобождения динамической памяти – это функция освобождения динамической памяти, выделенной ранее.

Краткие итоги

  1. В ходе выполнения программ выделяются статическая и динамическая области памяти.
  2. Возможны три варианта работы с динамической памятью: указатель определяется как локальный объект автоматической или статической памяти, указатель является глобальным объектом для блока памяти.
  3. Доступ к участкам динамической памяти осуществляется через динамические переменные.
  4. Работа с динамической памятью начинается с выделения участка памяти, а завершается освобождением ранее выделенного участка.
  5. Выделение и освобождение динамической памяти выполняется с помощью операций или функций для работы с динамической памятью.
< Лекция 24 || Лекция 25: 123 || Лекция 26 >
Денис Курбатов
Денис Курбатов
Владислав Нагорный
Владислав Нагорный

Подскажите, пожалуйста, планируете ли вы возобновление программ высшего образования? Если да, есть ли какие-то примерные сроки?

Спасибо!