Andi Pavllo
Andi Pavllo

Reputation: 2506

Find occurrences in a List using recursion in Haskell

I have the an List which can contain just two kind of elements, Apple and Peach. I need to create a function which, given a list with those elements, returns the number of occurences of Apple in the list by using recursion.

Here is my attempt:

data Fruit = Apple | Peach
findFruit :: [Fruit] -> Int

findFruit [] = 0

findFruit (y:ys)
    | y==Apple = 1+(findFruit ys)
    | otherwise = findFruit ys

But it's not working. I suspect the issue is in the last instructions but I cannot really understand where as I'm still a Haskell newbie.

Here is the error log:

Main.hs:7:8:
    No instance for (Eq Fruit) arising from a use of ‘==’
    In the expression: y == Apple
    In a stmt of a pattern guard for
                   an equation for ‘findFruit’:
      y == Apple
    In an equation for ‘findFruit’:
        findFruit (y : ys)
          | y == Apple = 1 + (findFruit ys)
          | otherwise = findFruit ys
Failed, modules loaded: none.

Thank you for your help!

Upvotes: 3

Views: 635

Answers (4)

Will Ness
Will Ness

Reputation: 71070

You can try for modularity and concept reuse with

import Data.Monoid

fruit a _ Apple = a    -- case analysis for Fruit 
fruit _ p Peach = p

countFruit = getSum . mconcat . map (fruit (Sum 1) (Sum 0))

(though it's not recursive).

Upvotes: 0

Michael Szvetits
Michael Szvetits

Reputation: 384

You can leave the data definition as it is and use pattern matching:

data Fruit = Apple | Peach

findFruit :: [Fruit] -> Int
findFruit []         = 0
findFruit (Apple:ys) = 1 + findFruit ys
findFruit (Peach:ys) = findFruit ys

Upvotes: 5

shree.pat18
shree.pat18

Reputation: 21757

You need to add deriving Eq to your type constructor. That way, the notion of equality for your type will be automatically implemented and the == operator will be valid for use.

data Fruit = Apple | Peach deriving Eq

Upvotes: 3

Netwave
Netwave

Reputation: 42678

Your code is ok, but he does not know how to compare elements, so, just derive from eq as the compiler is telling you:

data Fruit = Apple | Peach deriving (Eq)

This way the compiler will have information about this data can be compared.

Upvotes: 1

Related Questions