Массивы экземпляров класса

 

Из экземпляров класса можно создавать массивы. Создадим, например, статический массив из 6 экземпляров классаt_DinArr:

t_DinArr A [ 6 ];

Инициализируем экземпляры в этом массиве так:

for ( int i = 0; i < 6; ++ i )

A [ i ].Init ( i + 1 );

В результате мы получили массив на 6 элементов, в котором каждый элемент представляет собой динамический массив с количеством элементов, равным номеру этого динамического массива (элемент A [ 0 ]содержит экземпляр класса t_DinArrс массивом длиной 1 элемент; элемент A [ 1 ]содержит экземпляр класса t_DinArrс массивом длиной 2 элемента; элемент A [ 2 ]содержит экземпляр класса t_DinArrс массивом длиной 3 элемента и т.д. до элемента A [ 5 ],которыйсодержит экземпляр класса t_DinArrс массивом длиной 6 элементов;

Заполним эту конструкцию некоторыми данными:

for ( int i = 0; i < 6; ++ i )

for ( int j = 0; j < A [ i ].Count ( ); ++ j )

A [ i ].Set ( j, j );

Теперь выведем все эти значения на экран:

for ( int i = 0; i < 6; ++ i )

{

for ( int j = 0; j < A [ i ].Count ( ); ++ j )

cout << A [ i ].Get ( j ) << ‘ ‘;

cout << endl;

}

На экране получим:

0 1

0 1 2

0 1 2 3

0 1 2 3 4

0 1 2 3 4 5

 

Дополнительные замечания по работе с массивами экземпляров объектов классов приводятся в параграфе 13.5.

Встроенные члены функции

В рассмотренном выше примере класса реализация всех функций членов класса осуществлялась после описания самого класса (раздельная, внешняя реализация функций членов). Реализацию некоторых функций членов можно включать непосредственно внутрь описания самого класса. Например, тот же самый класс можно описать так:

 

// Описание класса

 

class t_DinArr {

// Закрытые члены-данные класса

t_Inf *Arr;// Указатель на динамический массив

unsigned ItemCount;// Количество элементов в массиве

public:

// Открытые члены-функции класса

// ----------------------------------------------

//Инициализация массива из N элементов

void Init (unsigned N = 0)

{

If (N)

Arr = (t_Inf *) malloc ( sizeof(t_Inf) * N );

Else

Arr = 0;

ItemCount = N;

Clear();

}

// ----------------------------------------------

// Очистка массива

Void Clear();

// ----------------------------------------------

// Запись значения Val в элемент с индексом Ind

Void Set (unsigned Ind, t_Inf Val)

{

if (Ind >= ItemCount)

cout << Err << Ind << '!\n';

Else

Arr [Ind] = Val;

}

// ----------------------------------------------

// Возвращает значение элемента с индексом Ind

T_Inf Get (unsigned Ind)

{

if ( Ind >= ItemCount )

{

cout << Err << Ind << "!\n";

Return DefVal;

}

Else

return Arr [ Ind ];

}

// ----------------------------------------------

// Добавляет в конец массива элемент со значением Val

Void Add ( t_Inf Val )

{

++ ItemCount;

Arr = ( t_Inf * ) realloc ( Arr, sizeof(t_Inf) * ItemCount );

Arr [ ItemCount - 1 ] = Val;

}

// ----------------------------------------------

// Возвращает количество элементов массива

unsigned Count () { return ItemCount; }

// ----------------------------------------------

// Удаление массива из динамической памяти

Void Free ()

{

If (Arr)

{

Free(Arr);

Arr = 0;

ItemCount = 0;

}

}

} ;

// Описание класса закончено

 

// И еще одна функция член класса, реализованная отдельно

// Очистка массива значениями DefVa

void t_DinArr :: Clear () l

{

for (unsigned i = 0; i < ItemCount; ++ i)

Arr [i] = DefVal;

}

Это определение класса t_DinArrотличается от предыдущего тем, что реализация всех членов функций (за исключением одной – функции Clear) выполнены внутри описания класса. Только функция Clearреализована отдельно.

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

1. Те функции, реализация которых находится внутри описания класса, не требуют указания принадлежности к этому классу (префикс t_DinArr :: не нужен).

2. Функции, реализованные вне описания класса, обязательно должны содержать этот префикс.

Что лучше и почему функция Clearреализована отдельно?

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

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

Поэтому в качестве встраиваемых обычно используют небольшие по объему функции.

Более того, встраиваемые функции имеют некоторые ограничения по используемым внутри них инструкциям (см. раздел по inline функциям). В частности, встраиваемые функции не могут содержать циклов. По этой причине нам пришлось функцию Clear реализовать вне описания класса (содержит цикл).








Дата добавления: 2019-02-07; просмотров: 476;


Поиск по сайту:

При помощи поиска вы сможете найти нужную вам информацию.

Поделитесь с друзьями:

Если вам перенёс пользу информационный материал, или помог в учебе – поделитесь этим сайтом с друзьями и знакомыми.
helpiks.org - Хелпикс.Орг - 2014-2024 год. Материал сайта представляется для ознакомительного и учебного использования. | Поддержка
Генерация страницы за: 0.015 сек.