Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
A.doc
Скачиваний:
36
Добавлен:
09.04.2015
Размер:
5.6 Mб
Скачать

56 Глава 2

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

Переменные с определенным набором значений

Иногда у вас будет возникать потребность в переменных, которые могут прини- мать значения лишь из ограниченного набора допустимых значений, ссылаться на ко- торые удобно было бы по каким-то меткам — дни недели, например, или месяцы года. В С++ предусмотрено специальное средство для таких ситуаций, называемое перечис- лением (enumeration). Возьмем пример, который я упомянул — переменная, которая должна принимать значения, соответствующие дням недели. Вы можете определить ее следующим образом:

Этот оператор объявляет тип перечисления по имени Week и переменную thisWeek, являющуюся экземпляром перечислимого типа Week, которая может принимать толь- ко константные значения, указанные между фигурными скобками. Если вы попытае- тесь присвоить thisWeek что-то такое, что не входит в указанный набор, то это вызо- вет ошибку. Эти символические имена, перечисленные между скобками, называются перечислителями (enumerators). Фактически каждое из названий дней автоматиче- ски представляется компилятором как фиксированное целое значение. Первое имя в списке — Моп — получает значение 0, Tues будет 1 и так далее.

Вы можете присвоить одну из перечисленных констант в качестве значения пере- менной thisWeek:

Обратите внимание, что вам не нужно квалифицировать перечйслимые констан- ты именем перечисления. Значение thisWeek будет равно 3, потому что определен- ным в перечислении символическим константам присваиваются значения типа int по умолчанию, начиная с 0.

По умолчанию каждый последующий перечислитель на единицу больше значения предыдущего, но если вы предпочитаете явно указать начальное значение, отличное от 0, вы можете просто написать так:

Теперь константы перечисления будут равны от 1 до 7. Перечислители даже не обязаны иметь уникальные значения. Вы можете определить, что и Моп, и Tues долж- ны, например, иметь значение 1, с помощью следующего оператора:

Поскольку, по сути, типом переменной thisWeek является int, она займет 4 бай- та, как и все переменные перечислимого типа.

Имея определение перечисления, вы можете определить другую переменную того же типа:

Это определяет переменную nextWeek как перечисление, которое может прини- мать значения, специфицированные ранее. Вы даже можете пропустить ключевое

Данные, переменные и вычисления 57

слово enum в объявлении переменной, поэтому предыдущий оператор может быть переписан так:

При желании вы можете присвоить определенные значения всем перечислите- лям. Например, можно определить следующее перечисление:

Здесь вы определяете возможные значения переменной things как числовые эк- виваленты соответствующих символов. Если вы заглянете в таблицу ASCII в приложе- нии Б, то увидите, что коды этих символов в десятичном виде равны, соответствен- но, 44, 33 и 63. Как видите, значения перечислителей не обязательно должны идти в возрастающем порядке. Если вы не специфицируете все значения явно, то каждому перечислителю, значение которого не задано, будет присвоено значение на единицу больше предыдущего, как в нашем втором примере Week.

Если нет необходимости объявлять позднее другие переменные перечислимого типа, вы можете пропустить имя этого типа, например

:

Здесь объявлены три переменных, которые могут принимать значения от Моп до Sun. Поскольку тип перечислителя не указан, вы не можете позднее сослаться не него. Обратите внимание, что вообще вы не можете объявлять другие переменные типа этого перечисления, потому что повторять это определение также не разреша- ется. Попытка сделать это означала бы, что вы собираетесь переопределить значения от Моп до Sun, а это недопустимо.

Спецификация типа для перечислимых констант

Перечислимые константы по умолчанию имеют тип int, но вы также можете ука- зать их тип явно, добавив двоеточие и имя типа для констант вслед за именем типа перечисления в его объявлении. Тип перечислимых констант может быть знаковым либо беззнаковым целочисленным типом: short, int, long, char или же bool.

Таким образом, вы можете определить перечисление, представляющее дни неде- ли, следующим образом:

Здесь константы перечисления будут относиться к типу char, причем первая из них будет равна 0. Однако, имея константы типа char, вы, вероятно, предпочтете инициализировать их явно:

Теперь значения констант немного лучше отображают то, что они представляют, хотя не делают различия между Thursday и Tuesday или между Saturday и Sunday. Нет никаких проблем в том, что разные константы имеют одно и то же значение, но имена, конечно, должны быть уникальными.

А вот пример перечисления с константами типа bool:

Поскольку On имеет начальное значение true, то Off будет false. Если бы были еще указаны последующие константы перечисления, они по умолчанию получили бы чередующиеся значения.