9789
Комбинированные типы (записи)
Контрольная
Информатика, кибернетика и программирование
Комбинированные типы (записи) Записи и селекторы Комбинированные типы, как и регулярные типы, представляют собой правило формирования составных типов. В отличие от массивов, записи позволяют объединять значения РАЗЛИЧНЫХ типов и поэтому являются, ви...
Русский
2013-03-17
79.5 KB
18 чел.
Комбинированные типы, как и регулярные типы, представляют собой правило формирования составных типов. В отличие от массивов, записи позволяют объединять значения РАЗЛИЧНЫХ типов и поэтому являются, видимо, наиболее гибким механизмом построения данных.
Распространенным случаем является необходимость описать атрибуты (характеристики) некоторого объекта, представляемого и обрабатываемого в программе. Таким объектом может быть человек, некоторый вычислительный комплекс, письмо, посылаемое по почте и т.д. Во всех подобных случаях атрибуты объекта представляются значениями различных типов и поэтому для их описания не могут быть использованы массивы. Для описания объекта "человек" могут понадобиться, например, следующие характеристики:
• фамилия, имя и отчество (символьные массивы или строки);
• пол (перечислимый тип из двух значений);
• индекс специальности (целое), и т.д.
Для представления такой разнородной, но логически связанной информации удобно использовать комбинированный тип. Необходимо отметить, что в данном случае отдельные компоненты комбинированного типа, ввиду их различной природы, не могут идентифицироваться порядковыми номерами (индексами), как в массивах; поэтому для обозначения компонент используются идентификаторы. Таким образом, описание комбинированного типа представляет собой список описаний его элементов (которые называются также полями записи); каждое описание похоже на описание простой переменной. Список полей начинается служебным словом record и должен завершаться служебным словом end. Для примера, приведенного выше, описание комбинированного типа Person (человек) может выглядеть следующим образом:
type
Person = record
Name, SecondName, SurName : string[20];
Pol : ( Male, Female );
Speciality : word;
end;
(Последняя точка с запятой перед словом end может быть опущена).
Итак, структура записи состоит из фиксированного числа компонент (полей), каждое из которых имеет собственное (уникальное в пределах записи) имя и ПРОИЗВОЛЬНЫЙ тип. Следует подчеркнуть, что уникальность имен полей требуется только внутри записи; идентификаторы полей могут совпадать с другими идентификаторами текущего блока, а также с идентификаторами полей в других записях. В данном случае конфликта имен не возникает, так как идентификатор поля всегда выступает в программе в паре с переменной-записью (см. далее).
Имея в программе вышеприведенное описание, можно определить переменные данного типа, например:
var Sasha, Masha : Person;
Доступ к элементам (полям) записей производится с помощью конструкции, называемой селектор записи и имеющей следующий общий вид:
R . F
где R - переменная комбинированного типа, F - идентификатор поля. Для переменных, введенных выше, допустимы следующие конструкции:
Sasha.Name := 'Александр';
Masha.Name := 'Мария';
Sasha.Pol : = Male;
Masha.Pol := Female;
Masha.Speciality := Sasha.Speciality;
Комбинированные типы можно использовать для построения более сложных структур, например, массивов, состоящих из записей, или записей, в состав которых, в свою очередь, входят записи. Первый случай может быть проиллюстрирован такими примерами:
var Group : array[1..10] of Person;
DataBase : file of Person;
Для переменной Group доступ к полям записей, составляющих этот массив, производится следующим образом:
Group[i].Pol := Female;
if Group[j].Name='Борис'
then WriteLn(Group[j].SurName) ;
Рассмотрим теперь случай, когда в составе записи содержатся поля, имеющие также тип записи. Пусть для комбинированного типа Person необходимо хранить информацию о дате рождения человека. Эту информацию можно представить в виде трех полей в составе типа Person. Однако, логичнее для этого определить отдельный тип, так как в этом случае он может использоваться в описании других типов и переменных:
type
Date = record
Month : (Jan,Feb,Mar,Apr,May,June,July,
Aug,Sept,Oct,Nov,Decem);
Day : 1..31;
Year : 1900..2100
end;
Теперь введенный таким образом тип можно использовать в записи Person:
type
Person = record
Name,SecondName,SurName : string[20];
Pol : ( Male, Female );
Speciality : word;
BirthDay : Date
end;
Доступ к полям из элемента BirthDay производится по общим правилам, например:
Sasha.BirthDay.Year := 1983;
Masha.BirthDay.Month := Feb;
Таким образом, при записи селектора необходимо помнить, что слева от символа "точка" всегда должна находиться переменная типа запись (в наших примерах переменными типа запись являются Group[i].Sasha.BirthDay и т.д.), а справа - идентификатор поля этой записи.
Для более компактной записи селекторов Pascal имеет специальный оператор присоединения, позволяющий в ряде случаев опускать левые части селекторов. Этот оператор будет подробно описан далее.
Будучи определенным в программе, некоторый комбинированный тип может использоваться наравне со всеми другими типами. Кроме образования с его участием других типов, комбинированный тип может употребляться для спецификации параметров подпрограмм (см. лекцию «Подпрограммы»). Например, можно определить специальный тип для представления комплексных чисел как пары вещественных переменных (действительную и мнимую части комплексного числа):
type
Complex = record
Re, Im : real
end;
Далее можно с помощью процедур определить операции над комплексными числами (сложение, умножение, деление):
procedure AddC ( C1, C2 : Complex, var R : Complex );
procedure MultC ( C1, C2 : Complex, var R : Complex );
procedure DivC ( C1, C2 : Complex; var R : Complex );
Понятие записи в языке Pascal предусматривает одну не вполне тривиальную возможность. Довольно часто бывает необходимо в пределах одной записи иметь различную информацию в зависимости от конкретного значения некоторого поля.
Рассмотрим опять тип Person, содержащий информацию о человеке. Если в этом типе поле Pol (пол) имеет значение Male (мужской), то пусть необходимо предусмотреть такие поля:
• время прохождения очередных военных сборов;
• курит человек или нет.
Если же это поле имеет значение Female (женский), то хотелось бы иметь информацию... например, о цвете глаз.
В принципе, можно было бы в таком случае определить два отдельных комбинированных типа PersonMale и PersonFemale, в которых и задать соответствующие поля.
Однако это сильно затруднит программирование общих для этих типов действий, поэтому в таких случаях используют записи с вариантами.
Любой комбинированный тип, помимо фиксированного списка полей, может содержать так называемую вариантную часть, предполагающую определение нескольких вариантов структуры этого типа. Это означает, что разные переменные, хотя и относятся к одному и тому же типу, могут иметь отличающуюся структуру. Различие может касаться как числа компонент, так и их типа.
Вариантная часть содержит несколько альтернатив, в каждой из которых в круглых скобках задается список полей, присущих данному варианту. Списку предшествует метка, являющаяся конкретным значением поля, которое является критерием выбора вариантов. Перечисление альтернатив начинается с определения этого поля.
В приведенной выше ситуации с типом Person запись с вариантами может иметь следующий вид:
type
PersonPol = ( Male, Female ) ;
Person = record
Name, SecondName, SurName : string[20];
Speciality : word;
BirthDay : Date;
case Pol : PersonPol of
Male : ( Army : Date;
Smoking : boolean );
Female : ( EyesColor: (Blue, Brown, Gray,
Green) )
end;
Обратите внимание на следующие обстоятельства:
Записи с вариантами представляют собой гибкий инструмент для представления информации, частично различающейся по своей структуре. Имея в программе вышеприведенный тип Person, можно объединить в логически связанные фрагменты манипуляции со всеми вариантами записей, например:
if Group[i].Pol = Male then
Group[i].Smoking := true
else
Group[i].EyesColor := Gray;
Дополнительно следует отметить, что любой вариант, в свою очередь, может иметь свою вариантную часть, которая также должна располагаться в конце списка полей данного варианта.
Однако при использовании вариантных записей необходимо учитывать следующие особенности:
Masha.Pol := Female;
Masha.Smoking := true;
будет выполнена, хотя поле Smoking не предусмотрено для значения Female в поле-дискриминанте Pol. Иными словами, в любое время возможен доступ ко всем полям во всех вариантах безотносительно значения дискриминанта. Считается, что за соответствием текущего значения дискриминанта и доступа к полям записи должен следить программист. Это, безусловно, может привести к различного рода логическим ошибкам и является одним из слабых мест языка.
В предыдущем рассмотрении полагалось, что конкретный вариант выбирается в зависимости от текущего значения поля-дискриминанта. Помимо такого механизма, возможен более простой случай, когда необходимо организовать доступ к различным полям вариантов безотносительно какого-либо условия.
Примером может служить схема доступа к регистрам процессора Intel 80x86. Известно, что к шестнадцатиразрядным регистрам общего назначения, именуемым обычно как АХ, ВХ, СХ, DX, возможен доступ и как к единым словам, и к отдельным их байтам; в последнем случае младшие и старшие части регистров обозначаются как АL,АН для регистра AX; BL,BH для регистра ВХ и т.д., причем можно произвольным образом чередовать обращение как к регистру в целом, так и к его частям.
Turbo Pascal имеет возможность непосредственного обращения к аппаратным регистрам посредством процедур специального вида. Для этих целей предусмотрено следующее программное представление регистров:
type
Registers = record
case integer of
0:(AX,HX,CX,DX,HP,SI,DI,DS,ES,Flags:word) ;
1:(AL,AH,BL,BH,CL,CH,DL,DH :byte)
end;
Здесь дискриминант представляет собой только идентификатор (дискретного) типа, который в данном случае определяет не специальное поле, а просто задает тип констант, которыми будут "пронумерованы" варианты. Имея в виду, что для всех вариантов записи отводится общая область, легко видеть, что память, отведенная для поля АХ, будет совмещена с памятью для полей AL, АН, и т.д.
Этот оператор предназначен для более наглядной и эффективной организации работы с значениями комбинированных типов. Если в некотором месте программы сосредоточено несколько операторов, манипулирующих с полями определенной записи, то эта часть программы будет выглядеть достаточно громоздко из-за необходимости обозначать каждое обращение к полю записи составным именем. Например, если необходимо произвести несколько операций над записью MyDate (см. ранее), то соответствующий фрагмент программы будет выглядеть следующим образом:
if MyDate.Month=12
then
begin
MyDate.Month := 1;
MyDate.Year := MyDate.Year+1
end
else MyDate.Month := MyDate.Month+1;
Существует возможность "вынести" общий для всех составных имен идентификатор записи в отдельный заголовок, после которого указывать поля записи посредством только их идентификаторов. Соответствующая конструкция называется оператором над записями (или оператором присоединения). Приведенный выше фрагмент программы можно переписать, "добавив" к условному оператору заголовок, состоящий из служебного слова with, идентификатора переменной комбинированного типа и служебного слова do:
with MyDate do
if Month=12 then
begin
Month := 1;
Year := Year+1
end
else
Month := Month+1;
В последнем примере манипуляции с полями записи MyDate выглядят значительно компактнее и нагляднее, чем в первоначальном варианте. Более того, следует иметь в виду, что второй фрагмент будет выполняться быстрее, так как адрес записи Date в памяти будет вычислен только один раз при обработке конструкции with MyDate do. Еще большей эффективности можно достичь, если запись является, например, элементом массива:
var
DB : array[1..Max] of DateRec;
begin
with DB[i] do
Если фрагмент программы содержит операции над несколькими записями, то в операторе присоединения можно указать список необходимых переменных-записей, разделенных запятыми:
with V1, V2, V3 do S;
где V1, V2, V3 - переменные комбинированных типов, S - некоторый оператор.
Такая форма записи считается эквивалентной следующей:
with V1 do with V2 do with V3 do S;
В случае задания списка переменных-записей нужно иметь в виду, что если некоторый идентификатор F является полем, например, и V1, и V2, то он интерпретируется как V2.F, а не как V1.F, то есть идентификатор поля связывается с последней переменной-записью в списке with.
Необходимо помнить, что все идентификаторы в пределах оператора присоединения проверяются, можно ли интерпретировать их как поля записей, упомянутых в заголовке. Если это так, то они всегда понимаются именно таким образом, даже если в текущем блоке и доступны переменные с такими же идентификаторами.
В заключение приведем синтаксическую диаграмму для оператора над записями:
Оператор присоединения
Начальные значения для типизированных констант комбинированных типов задаются в виде списка пар вида "идентификатор поля записи - значение поля записи". Элементы пар разделяются двоеточием, пары отделяются друг от друга точной с запятой, а весь список пар заключается в круглые скобки:
1) type
Point = record
X, Y : real
end;
const
Center : Point = (X:10.0; Y:10.0);
2) type
Line = array[1..2] of Point;
const
MyLine : Line = ((X:1;У:2), (X:10;Y:10));
3) type
Day = record
Name : (Mon,Tue,Wed,Thu,Fri,Sat,Sun);
Num : 1..31;
Month : 1..12
end;
const
SomeDay : Day = (Name:Mon; Num:11; Month:3);
Поля должны указываться в том же порядке, как они следуют в определении типа записи. Должны быть проинициализированы все поля. Синтаксическая диаграмма для изображения записи показана ниже.
В заключение данной главы приведем синтаксические диаграммы для комбинированных типов:
Комбинированный тип
Список полей
Фиксированная часть
Вариантная часть
Дискриминант
Альтернатива
А также другие работы, которые могут Вас заинтересовать | |||
74574. | Метаморфизм | 53 KB | |
Преобразованию могут подвергаться любые горные породы осадочные магматические и ранее образовавшиеся метаморфические. В физикохимических условиях отличных от тех в которых образовались горные породы происходит изменение их минерального состава структуры и текстуры. без изменения химического состава метаморфизуемой породы и метасоматически т. | |||
74575. | Тектонические движения и деформации земной коры | 1.08 MB | |
Среди них различают следующие основные формы: моноклинали флексуры и складки. Складки это изгибы слоев горных пород без разрыва сплошности под действием давления. Складки являются основной формой пликативных дислокаций. Антиклинальными называются выпуклые складки в которых пласты падают в противоположные стороны а в центральных частях залегают более древние породы чем на периферии рис. | |||
74576. | Геологические науки и их задачи | 74 KB | |
Общим этот курс называется потому что рассматривает общие сведения о Земле начиная с положения Земли в мировом пространстве и кончая геологической деятельностью человека. Свое продолжение он находит в ряде последующих геологических дисциплин изучающих вопросы строения наружной оболочки Земли земной коры ее химический вещественный состав физические свойства геологическую историю. Каждая геологическая наука имея общую цель изучение Земли в то же время решает свои задачи. Историческая геология изучает историю и закономерности... | |||
74577. | СТРОЕНИЕ ЗЕМЛИ | 4.66 MB | |
В твердом теле Земли выделяют три внутренние оболочки: центральную ядро промежуточную мантию наружную земную кору рис. Как внутренние так и внешние оболочки объединяют под общим названием геосфер Земли. История изучения внутреннего строения Земли насчитывает несколько столетий и тесно связана с развитием представлений о происхождении Солнечной системы. | |||
74578. | ГЕОЛОГИЧЕСКОЕ ЛЕТОИСЧИСЛЕНИЕ (ГЕОХРОНОЛОГИЯ) | 3.1 MB | |
В первом случае определяют относительный возраст пород т. Во втором случае определяют абсолютный возраст пород который выражается в годах. Относительное летоисчисление При определении относительного возраста пород используют несколько методов. | |||
74579. | ВЕЩЕСТВЕННЫЙ СОСТАВ ЗЕМНОЙ КОРЫ | 974.5 KB | |
К физическим свойствам относят цвет блеск цвет черты плотность твердость спайность магнитность и некоторые другие. Твердость степень сопротивления минералов царапанию резанию. В полевой практике пользуются шкалой заменителей... | |||
74580. | ГЕОЛОГИЧЕСКАЯ ДЕЯТЕЛЬНОСТЬ МОРЯ | 479 KB | |
в океане заключено 86 общего количества воды гидросферы. Физические и химические свойства морской воды Температура морской воды. В поверхностном слое морей и океанов температура воды во многом зависит от климатических условий местности. Но начиная с некоторой глубины колебания температуры морской воды обусловленные климатическими условиями исчезают и далее с глубиной температура неуклонно понижается. | |||
74581. | Геологическая деятельность ветра | 707 KB | |
Во всех песчаных пустынях широко распространены продольногрядовые пески которые образуются при ветрах имеющих штопорообразный характер движения воздуха в горизонтальном направлении одного направления. Бугристые пески песчаные холмы высотой до 810 м неправильной формы закрепленные растительностью. | |||
74582. | Геологическая деятельность снега, льда | 902.5 KB | |
Общий объем льда содержащегося в ледниках оценивается в 30 млн. Для возникновения ледника необходимы низкая среднегодовая температура большое количество осадков выпадающих в виде снега а также наличие пологих склонов и впадин защищенных от солнца и ветра. Это и определяет неравномерность накопления снега и масштабов образования глетчерного льда основная его часть 995 сосредоточена в полярных областях и только 05 связано с высокогорными ледниками. Накапливается он в виде масс значительной мощности составляющих тело ледника. | |||