Haskell Typeclasses Guide — Eq, Ord, Show, Read, and Typeclass Deriving
In this tutorial, you will learn about Haskell Typeclasses Guide. We cover key concepts, practical examples, and best practices to help you master this topic.
Haskell typeclasses are interfaces defining operations that multiple types can implement -- Eq for equality, Ord for ordering, Show for string representation, Read for Parsing, with deriving providing automatic implementations for standard typeclasses.
Standard Typeclasses
-- Eq: equality comparison
(==) :: a -> a -> Bool
(/=) :: a -> a -> Bool
-- Ord: ordering
compare :: a -> a -> Ordering -- LT, EQ, GT
(<), (>), (<=), (>=) :: a -> a -> Bool
min, max :: a -> a -> a
-- Show: convert to String
show :: a -> String
-- Read: parse from String
read :: String -> a
Deriving
data Color = Red | Green | Blue
deriving (Eq, Ord, Show, Read, Enum, Bounded)
-- Automatic implementations:
Red == Red -- True
Red < Green -- True (constructors order)
show Red -- "Red"
read "Red" :: Color -- Red
[Red .. Blue] -- [Red, Green, Blue]
minBound :: Color -- Red
maxBound :: Color -- Blue
Custom Typeclass
-- Defining a typeclass
class Describable a where
describe :: a -> String
-- Instances
instance Describable Int where
describe n = "Integer: " ++ show n
instance Describable Bool where
describe True = "It's true!"
describe False = "It's false!"
-- Default implementation
class Json a where
toJson :: a -> String
toJson = show -- default
instance Json Int
toJson 42 -- "42"
Typeclass Constraints
-- Constrained polymorphic functions
addTwice :: Num a => a -> a -> a
addTwice x y = x + x + y + y
safeHead :: Ord a => [a] -> Maybe a
safeHead [] = Nothing
safeHead (x:xs) = Just x
-- Multiple constraints
showCompare :: (Show a, Ord a) => a -> a -> String
showCompare x y
| x < y = show x ++ " < " ++ show y
| x == y = show x ++ " == " ++ show y
| otherwise = show x ++ " > " ++ show y
Common Mistakes
1. Forgetting deriving
Without deriving (Show), print won't work. Without deriving (Eq), == won't work.
2. Using read without type annotation
read "42" is ambiguous. Use read "42" :: Int or in a typed context: x + read "42".
3. Conflicting instances
Instances for the same (type, typeclass) pair can only be defined once per program. Orphan instances cause problems.
Practice Questions
1. What does deriving (Show) do? Automatically generates a show instance that produces valid Haskell code representing the value.
2. How do you add a constraint to a function?
function :: (Typeclass a) => a -> Result. The constraint goes before the => arrow.
3. What is the difference between Eq and Ord? Eq provides == and /= for equality testing. Ord provides < , >, compare for ordering. Ord implies Eq.
FAQ
{{< faq question="Can I derive my own typeclasses?" >}} Not automatically. Deriving works for standard classes (Eq, Ord, Show, Read, Enum, Bounded). For custom classes, write the instance manually. {{< /faq >}}
{{< faq question="What is GeneralizedNewtypeDeriving?" >}}
An extension allowing newtypes to derive instances from their underlying type: newtype Age = Age Int deriving (Num, Show).
{{< /faq >}}
{{< faq question="What are multi-parameter typeclasses?" >}}
Typeclasses with multiple type parameters: class Convertible a b where convert :: a -> b. Requires MultiParamTypeClasses extension.
{{< /faq >}}
What's Next
Now learn about custom algebraic data types.
| Topic | Description | Link |
|---|---|---|
| Custom Types | Algebraic data types | {{< ref "15-custom-types" >}} |
| Modules | Haskell module system | {{< ref "16-modules" >}} |
Built by the developers of DodaTech
Doda Browser, DodaZIP & Durga Antivirus Pro