Перераховуються тип

Перераховуються тип (скорочено перерахування, англ. enumeration, enumerated type ) - В програмуванні тип даних, чиє безліч значень являє собою обмежений список ідентифікаторів.


1. Опис і використання

Перераховуються тип визначається як набір ідентифікаторів, з точки зору мови грають ту ж роль, що і звичайні іменовані константи, але пов'язані з цим типом. Класичне опис типу-перерахування в мові Паскаль виглядає наступним чином:

 type  Cardsuit  =  (  clubs  ,  diamonds  ,  hearts  ,  spades  )  ; 

Тут виробляється оголошення типу даних Cardsuit (карткова масть), значеннями якого може бути будь-яка з чотирьох перерахованих констант. Змінна типу Cardsuit може приймати одне із значень clubs, diamonds, hearts, spades, дозволяється порівняння значень типу перерахування на рівність чи нерівність, а також використання їх в операторах вибору (в Паскалі - case) в якості значень, що ідентифікують варіанти.

Використання перерахувань дозволяє зробити вихідні коди програм більш читаються, оскільки дозволяють замінити "Магічні числа", що кодують певні значення, що читаються імена.

На базі перерахувань до деяких мовах можуть створюватися типи-безлічі. У таких випадках безліч розуміється (і описується) як неупорядкований набір унікальних значень типу-перерахування.

Перераховуються тип може використовуватися в оголошеннях змінних і формальних параметрів функцій (процедур, методів). Значення перечислимого типу можуть присвоюватися відповідним змінним і передаватися через параметри відповідних типів у функції. Крім того, завжди підтримується порівняння значень перечислимого типу на рівність і нерівність. Деякі мови підтримують також інші операції порівняння для значень перечислимого типів. Результат порівняння двох перечислимого значень у таких випадках визначається, як правило, порядком проходження цих значень в оголошенні типів - значення, яке в оголошенні типу зустрічається раніше, вважається "менше" значення, що зустрічається пізніше. Іноді Перечіслімий тип або деякий діапазон значень перечислимого типу також може бути використаний в якості типу індексу для масиву. У цьому випадку для кожного значення вибраного діапазону в масиві є один елемент, а реальний порядок проходження елементів відповідає порядку слідування значень в оголошенні типу.


2. Реалізація

Зазвичай в процесі компіляції значення перерахувань представляються за допомогою цілих чисел. В залежності від конкретної мови програмування таке подання може бути або повністю приховано від програміста, або доступно йому за допомогою тих чи інших "обхідних маневрів" (наприклад, примусового перетворення значення типу перерахування до значення типу "ціле число"), або навіть керовано програмістом ( в таких випадках програміст має можливість явно вказати, якими числами будуть кодуватися всі або деякі значення типу-перерахування). У всіх варіантів є свої позитивні і негативні сторони. З одного боку, можливість використання числових значень констант, що становлять тип-перелік, особливо при зловживанні нею, позбавляє сенсу використання цих типів і створює небезпеку появи помилок (коли використовуються числові значення, для яких в типі немає відповідних констант). З іншого боку, явне управління значеннями дає деякі додаткові можливості. Наприклад, дозволяє використовувати типи-перерахування при організації інтерфейсу з модулями, написаними на інших мовах, якщо вони використовують або повертають кодовані цілими числами значення з деякого визначеного набору.

Ще одна можливість, яку дають перечислимого типи на рівні реалізації мови - економія пам'яті. При невеликому обсязі типу-перерахування для зберігання значення цього типу досить декількох бітів (вищенаведений тип Cardsuit вимагає всього два біти на значення, в той час як стандартне ціле число на більшості використовуваних архітектур займає 32 біта - в 16 разів більше), і компілятор може використовувати цей факт для ущільнення зберігання даних в пам'яті. Це може бути особливо важливо, якщо декілька значень типів-перерахувань зберігаються в одному записі - ущільнення записів при обробці великих їх кількостей може звільнити багато пам'яті. Правда, необхідно відзначити, що компілятори зазвичай не реалізують цю можливість, принаймні, останнім часом, коли комп'ютерна пам'ять істотно подешевшала.


3. Критика

Тип перерахування є традиційним для розвинутих мов програмування, використовується досить широко і часто сприймається як щось само собою зрозуміле. Тим не менш, цей тип також не обходиться без критики з боку теоретиків і практиків програмування. Так, при розробці мови програмування Оберон перечислимого типи потрапили в список можливостей, які були видалені з мови. Ніклаус Вірт, розробник мови, назвав такі причини:

  • "У все зростаючій числі програм непродумане використання перерахувань ... призводить до демографічного вибуху серед типів, що, в свою чергу, веде не до ясності програм, а до багатослівності" [1];
  • коли тип перерахування експортується модулем (тобто стає частиною інтерфейсу) порушується загальне правило - команда експорту типу експортує одночасно всі його елементи, тоді як для всіх інших типів експорт типу приховує його внутрішню структуру;
  • з точки зору забезпечення удобочітаемості програм ніщо не заважає замість перечислимого типу використовувати просто групу спільно визначених іменованих констант, особливо при наявності таких мовних механізмів, як модулі або класи.

З іншого боку, наприклад, в Java, спочатку не містить перечислимого типу, цей тип був згодом введений з міркувань не тільки зручності, але і надійності: проблема використання замість перерахувань груп іменованих констант в тому, що відсутній контроль з боку компілятора як за унікальністю значень констант, так і за можливістю випадкового присвоювання змінним значень, які не відповідають жодній з цих констант.


4. Опис перерахувань до різних мовах

4.1. Ada

У мові Ada перерахування задаються за допомогою ключового слова is і подальшого списку значень через кому:

 type  Cardsuit  is  (  clubs, diamonds, hearts, spades  )  ; 

4.2. C і мови з C-подібним синтаксисом

Початковий K & R (сокр.Керніган & Рітчі - творці мови) діалект C не мав перелічуваних типів, однак вони були додані в стандарті ANSI C.

 enum  cardsuit  {  CLUBS  ,  DIAMONDS  ,  HEARTS  ,  SPADES  }  ; 

Динамічні мови слабкою типізації з C-подібним синтаксисом (напр., perl або JavaScript), як правило, не мають перерахувань.


4.2.1. C + +

Перерахування в мові C + + прямо успадковують поведінку перерахувань мови C, за винятком того, що перераховуються тип в C + + - справжній тип, і ключове слово enum використовується тільки при оголошенні такого типу. Якщо при обробці параметра є перерахуванням, якесь значення з перерахування не обробляється (наприклад один з елементів перерахування забули обробити в конструкції switch), то компілятор може видати попередження про забутий значенні. [2]


4.2.2. C #

 enum  Cardsuit  {  Clubs, Diamonds, Spades, Hearts  }  ; 

4.2.3. Java

У первісній Java перерахувань не було, замість них пропонувалося використовувати класи зі статичними константами. Починаючи з версії 5 (1.5) перерахування були введені в мову, вони являють собою повноцінний клас, в який можна додавати довільну кількість полів і методів. Перерахування були введені для поліпшеного контролю за тіпобезопасностью. [3]

 enum  Cardsuit  {  Clubs, Diamonds, Spades, Hearts  } 

4.3. Haskell

У деяких мовах програмування (наприклад, в мові Haskell) за допомогою Алгебраїчних типів можна емулювати перерахування. Наприклад, так кодується булевський тип, який містить два ідентифікатора для подання значень істинності:

 data Bool = False | True 

Примітки

  1. Н. Вірт. Від модуля до Оберон - www.vspu.ac.ru/ ~ chul / wirth / frommodula / frommodula.htm
  2. Перерахування в C + + (c + + enum types) - www.quizful.net / page / enum-types-c
  3. Enums - link9
Перегляд цього шаблону Типи даних
Неінтерпретіруемие
Числові
Текстові
Покажчик

Адреса Посилання

Композитні
Інші

Логічний Нижчий тип Колекція Перераховуються тип Виняток First-class function Opaque data type Recursive data type Семафор Потік Вищий тип Type class Unit type Void

Пов'язані теми