Изучай Haskell во имя добра! (Липовача) - страница 92

или >True. Для наших целей удобно предположить, что он определён следующим образом:

>data Bool = False | True deriving (Ord)

Поскольку конструктор >False указан первым, а конструктор >True – после него, мы можем считать, что >True больше, чем >False.

>ghci> True `compare` False

>GT

>ghci> True > False

>True

>ghci> True < False

>False

Если два значения имеют одинаковый конструктор, то при отсутствии полей они считаются равными. Если поля есть, то выполняется их сравнение. Заметьте, что в этом случае типы полей должны быть частью класса типов >Ord.

В типе данных >Maybe>a конструктор значений >Nothing указан раньше >Just – это значит, что значение >Nothing всегда меньше, чем >Just <нечто>, даже если это «нечто» равно минус одному миллиону триллионов. Но если мы сравниваем два значения >Just, после сравнения конструкторов начинают сравниваться поля внутри них.

>ghci> Nothing < Just 100

>True

>ghci> Nothing > Just (–49999)

>False

>ghci> Just 3 `compare` Just 2

>GT

>ghci>Just 100 > Just 50

>True

Но сделать что-нибудь вроде >Just (*3) > Just (*2) не получится, потому что >(*3) и >(*2) – это функции, а они не имеют экземпляров для класса >Ord.

Любой день недели

Мы легко можем использовать алгебраические типы данных для того, чтобы создавать перечисления, и классы типов >Enum и >Bounded помогают нам в этом. Рассмотрим следующий тип:

>data Day = Monday | Tuesday | Wednesday | Thursday | Friday | Saturday | Sunday

Так как все конструкторы значений нульарные (не принимают параметров, то есть не имеют полей), допустимо сделать для нашего типа экземпляр класса >Enum. Класс типов >Enum предназначен для типов, для значений которых можно определить предшествующие и последующие элементы. Также мы можем определить для него экземпляр класса >Bounded – он предназначен для типов, у которых есть минимальное и максимальное значения. Ну и уж заодно давайте сделаем для него экземпляры всех остальных классов типов, которые можно сгенерировать автоматически, и посмотрим, что это даст.

>data Day = Monday | Tuesday | Wednesday | Thursday | Friday | Saturday | Sunday

>  deriving (Eq, Ord, Show, Read, Bounded, Enum)

Так как для нашего типа автоматически сгенерированы экземпляры классов >Show и >Read, можно конвертировать значения типа в строки и из строк:

>ghci> Wednesday

>Wednesday

>ghci> show Wednesday

>"Wednesday"

>ghci> read "Saturday" :: Day

>Saturday

Поскольку он имеет экземпляры классов >Eq и >Ord, допускаются сравнение и проверка на равенство:

>ghci> Saturday == Sunday

>False

>ghci> Saturday == Saturday

>True

>ghci> Saturday > Friday

>True

>ghci> Monday `compare` Wednesday

>LT