Online Book Reader

Home Category

Learn You a Haskell for Great Good! - Miran Lipovaca [56]

By Root 514 0
so the value of Nothing is always smaller than the value of Just something, even if that something is minus one billion trillion. But if we specify two Just values, then it will compare what’s inside them.

ghci> Nothing < Just 100

True

ghci> Nothing > Just (-49999)

False

ghci> Just 3 `compare` Just 2

GT

ghci> Just 100 > Just 50

True

However, we can’t do something like Just (*3) > Just (*2), because (*3) and (*2) are functions, which are not instances of Ord.

Any Day of the Week


We can easily use algebraic data types to make enumerations, and the Enum and Bounded type classes help us with that. Consider the following data type:

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

Because all the type’s value constructors are nullary (that is, they don’t have any fields), we can make it part of the Enum type class. The Enum type class is for things that have predecessors and successors. We can also make it part of the Bounded type class, which is for things that have a lowest possible value and highest possible value. And while we’re at it, let’s also make it an instance of all the other derivable type classes.

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

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

Now let’s see what we can do with our new Day type. Because it’s part of the Show and Read type classes, we can convert values of this type to and from strings.

ghci> Wednesday

Wednesday

ghci> show Wednesday

"Wednesday"

ghci> read "Saturday" :: Day

Saturday

Because it’s part of the Eq and Ord type classes, we can compare or equate days.

ghci> Saturday == Sunday

False

ghci> Saturday == Saturday

True

ghci> Saturday > Friday

True

ghci> Monday `compare` Wednesday

LT

It’s also part of Bounded, so we can get the lowest and highest day.

ghci> minBound :: Day

Monday

ghci> maxBound :: Day

Sunday

As it’s an instance of Enum, we can get predecessors and successors of days and make list ranges from them!

ghci> succ Monday

Tuesday

ghci> pred Saturday

Friday

ghci> [Thursday .. Sunday]

[Thursday,Friday,Saturday,Sunday]

ghci> [minBound .. maxBound] :: [Day]

[Monday,Tuesday,Wednesday,Thursday,Friday,Saturday,Sunday]

Type Synonyms

As mentioned earlier, when writing types, the [Char] and String types are equivalent and interchangeable. That’s implemented with type synonyms.

Type synonyms don’t really do anything per se—they’re just about giving some types different names so that they make more sense to someone reading our code and documentation. Here’s how the standard library defines String as a synonym for [Char]:

type String = [Char]

The type keyword here might be misleading, because a new type is not being created (that’s done with the data keyword). Rather, this defines a synonym for an existing type.

If we make a function that converts a string to uppercase and call it toUpperString, we can give it a type declaration of this:

toUpperString :: [Char] -> [Char]

Alternatively, we can use this type declaration:

toUpperString :: String -> String.

The two are essentially the same, but the latter is nicer to read.

Making Our Phonebook Prettier


When we were dealing with the Data.Map module, we first represented a phonebook with an association list (a list of key/value pairs) before converting it into a map. Here’s that version:

phoneBook :: [(String, String)]

phoneBook =

[("betty", "555-2938")

,("bonnie", "452-2928")

,("patsy", "493-2928")

,("lucille", "205-2928")

,("wendy", "939-8282")

,("penny", "853-2492")

]

The type of phoneBook is [(String, String)]. That tells us that it’s an association list that maps from strings to strings, but not much else. Let’s make a type synonym to convey some more information in the type declaration.

type PhoneBook = [(String,String)]

Now the type declaration for our phonebook can be phoneBook :: PhoneBook. Let’s make a type synonym for String as well.

type PhoneNumber = String

type Name = String

type PhoneBook = [(Name, PhoneNumber)]

Haskell programmers give type synonyms

Return Main Page Previous Page Next Page

®Online Book Reader