Similar presentations:
Лекция_7
1. Основы программирования Лекция 7
Структуры2. Определение
Для определения структуры применяетсяключевое слово struct, а сам формат
определения выглядит следующим образом:
struct имя_структуры
{
компоненты_структуры
};
Имя_структуры представляет произвольный
идентификатор, к которому применяются те же
правила, что и при наименовании переменных.
После имени структуры в фигурных скобках
помещаются компоненты структуры - объекты,
которые составляют структуру.
Следует отметить, что в отличие от функции при
определении структуры после закрывающей
фигурной скобки идет точка с запятой.
Например, определим простейшую структуру:
struct Student
{
int age;
char * name;
};
Здесь определена структура Student, которая
имеет два элемента: age (представляет тип int)
и name (представляет указатель на тип char).
Все элементы структуры объявляются как
обычные переменные. Но в отличие от
переменных при
определении
элементов
структуры для них не выделяется память, и их
нельзя инициализировать. По сути мы просто
определяем новый тип данных.
3. Использование
После определения структуры мыможем ее использовать. Для начала
мы можем определить объект
структуры - по сути обычную
переменную,
которая
будет
представлять созданный тип.
Здесь определена переменная stud,
которая
представляет
структуру Student. И при каждом
определении
переменной
типа
структуры ей будет выделяться
память, необходимая для хранения
ее элементов.
4. Инициализация
При определении переменной структуры ее можносразу инициализировать, присвоив какое-нибудь
значение. Инициализация структур аналогична
инициализации массивов: в фигурных скобках
передаются значения для элементов структуры. Есть
два способа инициализации структуры.
По позиции: значения передаются элементам
структуры в том порядке, в котором они
следуют в структуре. Так как в структуре Student
первым определено свойство age, которое
представляет тип int - число, то в фигурных
скобках
вначале
идет
число,
которое
передается элементу age. Вторым идет
элемент name, который представляет указатель
на тип char или строку, соответственно вторым
идет строка. И так далее для всех элементов
структуры по порядку.
По имени: значения передаются элементам
структуры по имени, независимо от порядка. В
этом
случае
перед
именем
элемента
указывается точка, например, .name.
5. Обращение к элементам структуры
Также после создания переменной структурыможно обращаться к ее элементам - получать их
значения или, наоборот, присваивать им новые
значения. Для обращения к элементам структуры
используется операция "точка":
имя_переменной_структуры.имя_элемента
Можно инициализировать элементы структуры
по отдельности:
6. Объединение определения и создания переменных
Мы можем одновременно совмещать определение типаструктуры и ее переменных:
Можно определить сразу несколько переменных, при
подобном определении мы можем даже не указывать имя
структуры:
После определения структуры, но до точки с запятой мы
можем указать переменные этой структуры. А затем
присвоить их элементам значения. Можно тут же
инициализировать структуру:
В этом случае компилятор все равно будет знать, что
переменная petr представляет структуры с двумя
элементами name и age. И соответственно мы также с
этими переменными сможем работать. Другое дело, что
мы не сможем задать новые переменные этой структуры в
других местах программы.
7. Определение структуры с использованием typedef
Еще один способ определенияструктуры представляет ключевое
слово typedef.
В конце определения структуры
после закрывающей фигурной скобки
идет ее обозначение - в данном
случае Student. В дальнейшем мы
можем
использовать
это
обозначение
для
создания
переменной структуры. При этом в
отличие от примеров выше здесь при
определении переменной не надо
использовать слово struct.
8. Копирование
Одну структуру можно присваиватьдругой структуре того же типа. При
копировании элементы структуры
получают копии значений.
В переменную ivan копируются
данные из структуры petr. Далее для
структуры ivan меняется значение
поля name.
9. Ввод данных с консоли
Сэлементами
структуры
можно
производить все те же операции, что и с
переменными тех же типов.
10. Вложенные структуры
Кроме базовых примитивных типов данных как intили char, массивов и указателей в качестве
элементов структуры можно использовать другие
структуры.
Структура Date представляет некоторую дату, ее
элементы day, month и year представляют день,
месяц и год соответственно. А структура Student
представляет студента, в котором определено три
элемента: name - имя, surname - фамилия и birth –
дата рождения. Последний элемент в свою очередь
представляет структуру Date. И чтобы обратиться к
полям вложенной структуры, надо сначала
обратиться к самой этой структуре:
petr.birth.day
И подобное обращение будет применяться при всех
операциях с элементами вложенной структуры Date.
11. Обращение к элементам вложенных структур
12. Инициализация вложенных структур
При инициализации структуры сразу можноинициализировать и вложенную структуру.
Поскольку структура Student имеет три элемента,
и последний элемент составной и сам содержит
три элемента, то при инициализации структуры
нам надо ей передать 5 значений.
Значения вложенной структуры заключаются во
внутреннюю пару фигурных скобок.
Передача значений идет в том порядке, в
котором элементы определены в структуре, в
том числе во вложенных структурах.
13. Указатели на структурный тип Обращение через указатель
На структуры, как и на объекты других типов,можно определять указатели. В качестве
значения такому указателю присваивается адрес
объекта структуры того же типа.
Используя указатель на структуру, можно
получить доступ к ее элементам. Для этого
можно воспользоваться двумя способами.
Первый способ представляет
операции разыменования:
применение
(*указатель_на_структуру).имя_элемента
Второй способ предполагает
операции -> (операция стрелка):
использование
указатель_на_структуру->имя_элемента
14. Ссылка структуры на саму себя
Элементы структуры могут представлять указатель на структуруэтого же типа. Подобная ситуация встречается довольно часто в
различных типах данных, которые состоят из связанных звеньев,
например, в связных списках, где каждый элемент имеет
указатель на следующий и/или предыдущий элемент этого же
типа структуры.
Структура pizza имеет два элемента. Элемент value хранит
собственно некоторое значение. А элемент next представляет
указатель на следующий объект структуры pizza.
Таким образом, фактически получается цепочка Crudo - Romana Sarda или грубо говоря список объектов структуры pizza.
Используя эти указатели, можно перемещаться вперед по этому
списку. Далее в цикле while, пока указатель pointer не будет
указать ни на какой объект структуры (то есть будет равен NULL),
выводится значение value текущего объекта, на который
указывает pointer, и затем происходит присваивание ему
значения указателя pointer->next, то есть осуществляется
переход к следующей структуре в списке.
Таким образом, можно определять связанные наборы объектов,
не прибегая к массивам.
15. Массивы структур
Из структур можно создавать массивы также, какмассивы других типов. И все форматы
определения массива структур будут аналогичны
определению массивов других типов. Обращение
к элементам массива структур происходит по
индексу students[0]. А чтобы обратиться к
элементу структуры из массива, после индекса
указывается
имя
элемента
структуры:
students[i].name
16. Динамические массивы структур
17. Структура в качестве параметра функции
18. Структура в качестве возвращаемого типа функции (начало)
19. Структура в качестве возвращаемого типа функции (продолжение)
20. Перечисления (enum)
Перечисления представляют типы данных, которыесодержат набор констант, и каждой константе
сопоставлено определенное числовое значение.
Перечисление определяется с помощью ключевого
слова enum:
enum название_перечисление { константа1, константа2,
... , константаN };
После слова enum идет название перечисления, затем в
фигурных
скобках
перечисляются
константы
перечисления.
В примере определено перечисление, которое
называется operation и которое условно представляет
математическую операцию. Оно определяет три
константы: ADD, SUBTRACT и MULTIPLY. В функции main
определяется переменная перечисления, которой
можно присвоить одну из констант перечисления.
Далее можно использовать эту константу. В примере
осуществляется вывод ее значения на консоль в виде
числа. Каждой константе будет присваиваться
числовое значение: первой константе - число 0, второй
константе - число 1, третей - 2 и так далее.
21. Присвоение конкретных значений элементам перечислений
Можно явным образом присвоить константамчисловые значения, если по каким-то
причинам не устраивают значения по
умолчанию. Либо есть возможность указать
значение для первой константы, тогда все
последующие будут получать значение на
единицу больше.
Либо можно присвоить всем уникальные
значения.
22. Использование перечислений
Нередко константы перечисления выступают в качественабора состояний, и в зависимости от состояния
программа выполняет ту или иную логику.
В примере определена функция calculate(), которая
выполняет арифметическую операцию. Первые два
параметра функции представляют два числа, над
которыми выполняется операция. А третий параметр значение перечисления operation представляет тип
операции. В самой функции в зависимости от третьего
параметра выполняется та или иная операция и
возвращается ее результат.
В функции main три раза вызывается функцию calculate с
одними и теми же числами, но разными типами операций.
Конечно, можно обойтись и без перечислений, используя
обычные
числа.
Но,
во-первых,
перечисления
представляют для своих констант описательные имена,
которые часто говорят сами за себя, например,
ADD(сложение). Во-вторых, в случаем с перечислением мы
имеем дело с ограниченным набором констант, которыми
проще управлять, нежели разрозненными числами.
23. Объединения (union)
Наструктуры
во
многом
похожи
объединения. Объединения (union) также позволяют
определить свой тип данных и также хранят набор
элементов, но в отличие от структуры все элементы
объединения имеют нулевое смещение. А это значит, что
разные элементы занимают в памяти один и тот же
участок, то есть в памяти они накладываются друг на
друга.
Для определения объединений применяется ключевое
слово union и следующий формальный синтаксис:
union имя_объединения
{
тип элемент1;
тип элемент2;
.............
тип элементN;
};
Объединение ascii хранит в одном и том же участки
памяти объект int (числовой код символа) и объект char
(сам символ). Конкретный размер выделенной памяти
будет зависеть от системы и реализации. В этом случае
объединение на большинстве платформ будет занимать 4
байта. Длина элементов может быть разной, и в этом
случае размер объединения вычисляется по наибольшему
элементу.
После определения объединения можно создать его
переменную и присвоить ей какое-либо значение. При
определении переменной объединения ее можно сразу
инициализировать,
но
стоит
учитывать,
что
инициализировать можно только первый элемент
объединения. В данном случае это элемент digit типа int.
Стоит отметить, что, так как оба элемента - letter и digit
занимают одну и ту же память, то данные фактически одни и
те же, только при обращении к code.digit данные
интерпретируются как объект int, а при обращении
к code.letter - как объект char.
24. Анонимные объединения и установка псевдонимов
Существуетвозможность
анонимные объединения:
определять
А с помощью оператора typedef можно
задать псевдоним для объединения:
25. Использование объединений
Ключевая возможность объединений состоит в том, чтоони могут применяться для хранения значений разных
типов. В данном примере определяется структура node,
которая имеет два поля - тип структуры в виде
перечисления node_type и непосредственно данные
структуры в виде поля node_data. Перечисление
node_type может принимать два значения - NODE_STRING
и NODE_INT, указывая, что структура будет хранить
соответственно или строку, или целое число. Если
структура представляет число, то для обращения к
данным используется поле int_value, а если строку - то
поле str_value
Для упрощения вывода данных структуры node
определена
отдельная
функция
print_node().
В
зависимости от типа структуры обращение идет к полю
n.data.str_value или n.data.int_value .
programming