Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
ПЯВУ - методичка2.doc
Скачиваний:
1
Добавлен:
01.04.2025
Размер:
403.97 Кб
Скачать

Вложенные структуры

Одним из полей структуры (внешней) может быть другая структура (внутренняя, вложенная). При этом возможны два способа описания шаблона.

Способ 1. Совместное описание структур (внешней и вложенной):

struct STUDENT { char name [30]; /* поле внешней структуры */

struct { int day ; /* шаблон вложенной структуры */

int month ;

int year ;

} born ; /* поле вложенной структуры */

} ;

Такое описание шаблонов выглядит громоздким.

Способ 2. Раздельное описание шаблонов:

struct DATA { int day; int month ; int year ; } ; /* шаблон структуры */

struct STUDENT { char name [30] ; /* поле внешней структуры */ struct DATA born ; /* поле вложенной структуры */ } ;

Глубина вложения структур неограниченна. Единственное ограничение – структура не может вкладываться сама в себя, то есть некорректно следующее описание:

struct STUDENT{ char name [30] ;

struct STUDENT my_own ; /* ОШИБКА !*/

};

Однако разрешается использовать в описываемом шаблоне поле-указатель (ссылку) на описываемую структуру, например, корректно такое описание:

struct STUDENT { char name [30] ;

struct STUDENT *my_own; /* допустимый указатель на собственную структуру */

};

Обращение к полям структуры

Для доступа к отдельным полям структурной переменной (не указателя) используется операция ‘’ (точка), формирующая ссылку на поле по схеме:

переменная  поле

Например, для переменных, описанных шаблоном

struct STUDENT { char name [30] ; int ball [4] ; float sb ;

} st1, st2, gr [20] , *pst ;

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

st1.name – указатель-константа на первый элемент массива name,

st2.ball [1] – ссылку на элемент с индексом 1 массива ball,

&st1.sb – адрес первого байта поля sb,

а также возможны ссылки вида gr [i].ball [4], gr [i+1].ball[k +1] и т.д.

Ссылка на поле структурной переменой обладает всеми свойствами обычной переменной. Корректны следующие выражения:

scanf (“%s”, st1.name) ; /* ввод Фамилии И.О. */

st.sb = 0 ; /* обнуление поля структуры */

gr [i].sb = st1.sb ; /* копирование поля структуры */

strcpy (gr [i].name, st1.name) ; /* вызов библиотечной функции */

Если структурные переменные описаны одним и тем же шаблоном, допускается операция присваивания таких структурных переменных, например,

st2 = st1; /* переменная st1 предварительно должна быть определена */

gr[i] = st1;

Операция присваивания структурных переменных приводит к пересылке (копированию) в памяти всех байтов одной переменной другой переменной.

Для доступа к полям структурной переменной через указатель используется операция ‘->’ (стрелка) по схеме:

указатель -> поле_структуры .

Ссылка на поле структурной переменной через указатель может участвовать в выражениях и операторах аналогично простой переменной, например,

pst1 = &st1; /* запись адреса структуры в указатель */

pst1 -> name = ”Иванов А.С. ”; /* запись литерала в поле name */

scanf (“%f”, &pst ->sb); /* запись числа в поле sb */

Вообще говоря, ссылка на поле структурной переменной через указатель – это синоним ссылки на данное поле через операцию ‘.’, например ссылка pst ->sb может быть записана, как (*pst).sb.

Ссылка на поле вложенной структуры формируется в виде цепочки имен переменной и полей структур по схеме (для не указателя):

переменная . имя_внешней_структуры . поле_внутренней_структуры

Например, для описания структур и структурных переменных:

struct data { int day; int month; int year;}; /* шаблон структуры */

struct STUDENT { char name[30];

struct DATA born; /* вложенная структура */

} st, *pst=&st ; /*переменная и указатель на структуру*/

возможны выражения:

st.born.day = 15;

st.born.month = 2;

st.born.year = 1979;

В общем случае доступ к полям вложенных структур подчиняется правилу : если в цепочке переменных и полей есть указатель, то доступ через него осуществляется по операции ‘->’, а если не указатель – по операции ‘.’, например,

pst->born.day = 20;.

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

Например, предыдущее описание структур можно изменить:

struct STUDENT { struct DATA *pborn; /* struct DATA описана ниже */

char name [30];

};

struct DATA { int day; int month; int year; /* шаблон структуры */

} ;

struct student st, *pst=&st; /* переменная и указатель на структуру */

Доступ к полям в операторах с указателями:

pst -> pborn -> day = 25; /* запись числа в поле day */

scanf (“%d”, &pst -> pborn -> month); /* ввод числа в поле month */