Non-exhaustive patterns in function (Haskell) [duplicate] - list

This question already has answers here:
Non exhaustive pattern in function in GHCi
(2 answers)
How do I use multiple where clauses in GHCi?
(2 answers)
Function definition by special cases in GHCi
(2 answers)
Closed 4 years ago.
I have two code snippets that throw the same error:
Prelude> sum' [] = 0
Prelude> sum' (x:xs) = x + sum' xs
Prelude> sum' [1,2,3,4,5]
*** Exception: <interactive>:142:1-25: Non-exhaustive patterns in function sum'
and the following as well:
Prelude> prod [] = 1
Prelude> prod (x:xs) = x * (prod xs)
Prelude> prod [1,2,3,4,5]
*** Exception: <interactive>:139:1-27: Non-exhaustive patterns in function prod
I must be missing a pattern, but what is it? Also, how do I such errors? How should I think when defining a function using pattern matching? (I'm asking for a methodolgy/technique)

To create a function with pattern matching, or using multi line in the command line of ghci you should use {} and separate with ; in your case:
Prelude> let { sum' [] = 0 ; sum' (x:xs) = x + sum' xs }
Prelude> sum' [1,2,3,4,5]
=> 15
otherwise you will be binding only one equation (in this case the last one) to the function name sum' and that's why you get a pattern matching failure

Related

Warning: match nonexhaustive - handling a specific case (SML)

Consider the following example of a list in SML: [[("foo",~10.0)],[("goo",~8.0)]].
I would link to write a function which will delete the main brackets meaning the output will be:
[("foo", ~10.0), ("goo, ~8.0)]
The function I wrote:
fun inner_list [[]] = [] | inner_list [] = []
| inner_list ((((x:(string*real))::xt)::xs)) = x :: inner_list xs;
It works for most cases but I know that I didn't check one of the cases. I think this case is:
[[],("foo", ~10.0)]
I know that I didn't handle one of the cases because the compiler alerts:
stdIn:1.6-2.68 Warning: match nonexhaustive
nil :: nil => ...
nil => ...
(x :: xt) :: xs => ...
I read other articles related with the Warning: match nonexhaustive warning, but I didn't understand how to solve it with my program.
How to handle the other case?
EDIT I know that my list contains only one list. this is why I don't use xt
How about the built-in List.concat?
List.concat [[("foo",~10.0)], [("goo",~8.0)]] =
[("foo",~10.0), ("goo",~8.0)]

Haskell Beginner, recursive function, list, Error: Non-exhaustive patterns

i try to write a function [int] -> int to count the sum of a list of integers with an iterative function (result should equal the build in function sum)
19>sumList :: [Int] -> Int
20>sumList [list] | length[list] > 0 = [list]!!0 + sumList (drop 1 [list])
21> | otherwise = 0
This is the result if i try to run it
uebung1.lhs:20:2: warning: [-Wincomplete-patterns]
Pattern match(es) are non-exhaustive
In an equation for ‘sumList’:
Patterns not matched:
[]
(_:_:_)
Ok, modules loaded: Main.
*Main> sumList []
*** Exception: uebung1.lhs:(20,2)-(21,31): Non-exhaustive patterns in function sumList
*Main> sumList [3]
*** Exception: uebung1.lhs:(20,2)-(21,31): Non-exhaustive patterns in function sumListi i i i i
What have i done wrong? I've slept a night over it but i just dont see where the problem is. The guarded equations should catch all cases of list lengths. Thanks for any advise.
The problem is that your pattern matches only a list with one element.
For example, if you try to define a function in ghci:
a [x] = x
And then try to call it with the lists with a different number of elements:
a [1] results with 1
a [] results with Exception: <interactive>:5:1-13: Non-exhaustive patterns in function a
a [1,2] results with Exception: <interactive>:1:1-9: Non-exhaustive patterns in function a
The following modification makes your function work:
sumList :: [Int] -> Int
sumList list | length list > 0 = list!!0 + sumList (drop 1 list)
| otherwise = 0
But, certainly, the following definition would be more idiomatic and performant:
sumList :: [Int] -> Int
sumList [] = 0
sumList (x:xs) = x + sumList xs
By (x:xs) pattern you immediately receive x as a head of your list (list!!0) and xs as a tail of it (drop 1 list)
The function will not work for an empty list, or any list with more than one item.
Your problem is that you are matching against [list], a list with one member which is list. Instead, try matching against just list. This means it will match anything of type [Int] from your type signature.
I get your confusion, as the type [a] is for lists of any length, but [a] will only match a list of one element.
I have also attached another way of writing your function using pattern matching, which hopefully you will find useful.
sumList :: [Int] -> Int
sumList [] = 0
sumList (x:xs) = x + sumList xs
It is unusual to use guards, but you did, your code would look like this:
sumList :: [Int] -> Int
sumList list
| length list > 0 = head list + sumList (tail list)
| otherwise = 0
Notice how [list] has been replaced by list, and !! 0 has been replaced by head, and drop 1 has been replaced by tail.
Hoogle is your friend!
You could also move the check for an empty list to the first guard, like so:
sumList :: [Int] -> Int
sumList list
| list == [] = 0
| otherwise = head list + sumList (tail list)
Note how similar this code is to the pattern matching code.
Others have already answered, but I want to stress that the warning emitted by the compiler spotted the issue:
Pattern match(es) are non-exhaustive
In an equation for ‘sumList’:
Patterns not matched:
[]
(_:_:_)
This is saying that the code is not handling some cases in its pattern matching. The empty list [] above is reported as non-matched, meaning that the program will crash on the empty list. Also, the lists of the form (_:_:_) are not matched: these are lists having at least two elements, such as 1:2:rest which is a list starting with elements 1 and 2 and then proceeding with list rest for the next elements.
So, the warning is telling us that we only handle lists of length one. Indeed, we only handle the pattern [_], which is the same of _:[] -- a list starting with one element and then ending there.
If you are a beginner, I think you did not learn pattern matching yet. This should be your priority for learning Haskell: it is one of the most important features. Generally speaking, if your recursive code uses length, !!, tail, head it is very likely that your are doing it wrong. There are some places where these functions are needed, but in many simple exercises they are not, pattern matching being usually sufficient and elegant.

Multiply all numbers in a list - Haskell [duplicate]

This question already has answers here:
product of list iteratively
(2 answers)
Closed 6 years ago.
I'm really new to haskell and would like to multiply all numbers in an array. For example.:
Array:
[3,2,4] //3*2*4
Output
24
Thanks, any help is greatly appreciated.
There are a number of ways of doing it in Haskell.
For instance, you could use:
product [3,2,4]
or equivalently
foldr (*) 1 [3,2,4]
or recursively:
prod [] = 1
prod (x : xs) = x * prod xs
Function foldr is the so called list catamorphism. To understand foldr we need to first understand list constructors. In Haskell, [3,2,4] is a syntax sugar for 3 : 2 : 4 : [], where : is list-cons constructor and [] is the empty list. Application foldr f v replaces every occurrence of : in a list by function f and the empty list for v. Its definition is as follows:
foldr :: (a -> b -> b) -> b -> [a] -> b
foldr f v [] = v -- equation 1
foldr f v (x:xs) = f x (foldr f v xs) -- equation 2
As an example, consider foldr (*) 1 [3,2,4]:
foldr (*) 1 [3,2,4] =
3 * (foldr (*) 1 [2,4]) = (by equation 2 of foldr)
3 * (2 * (foldr (*) 1 [4])) = (by equation 2 of foldr)
3 * (2 * (4 * (foldr (*) 1 []))) = (by equation 2 of foldr)
3 * (2 * (4 * 1)) = (by equation 1 of foldr)
= 24
You can do so with a fold function:
foldr (*) 1 [2,3,4]
or...
foldr1 (*) [2,3,4]
The product function is exactly what you're looking for.
It has also the feature that product [] equals 1, as you would expect mathematically speaking.
If you look at its definition, you can see that product is indeed the fold of multiplication (with 1 as neutral element).

Function for infinite list excluding multiples of three

This question is related to my previous question Removing items from a list if a predicate holds .
I am struggling with outputting an infinite list which does not contain any multiple of three.
For that I have these few functions till now:
delete :: Eq a => a -> [a] -> [a]
delete deleted xs = [ x | x <- xs, x /= deleted ]
removeif ::(a -> Bool)->[a]->[a]
removeif func [] = []
removeif func (h:t)= if func h then delete h (h:t) else removeif func t
nothreefolds :: [Integer]
nothreefolds = removeif (x `mod` 3 == 0) [1..]
But the problem is that I am missing some syntax knowledge and I want to tell removeif to remove the elements from natural numbers if they are multiple of 3.
If you can please help me to the right direction, I will be thoroughly grateful.
removeif wants a function as first argument. But x `mod` 3 == 0 is not a function. It's an expression that references a non-existing name x.
You want to use a lambda abstraction: \x -> x `mod` 3 == 0.
The \x -> part says that this is a function with one parameter called x.
The result is given by the following expression.
Alternatively you could simply use sections and function composition: (== 0) . (`mod` 3).
Using composition :
removeThreeMultiple = filter ( (/= 0) . (`mod` 3))
Example:
Prelude> removeThreeMultiple [1,2,3,4,9,0]
[1,2,4]
Make it simple, try to write correctly the intermediate function that checks if a number is a mutliple of three or not. Then use it to clean your list.

Why does pattern matching not cover list heads in Haskell? [duplicate]

This question already has answers here:
Pattern matching equivalent variables in Haskell, like in Prolog
(3 answers)
Closed 9 years ago.
I want to use the following code/ functionality in Haskell:
test :: String -> String -> Bool
test (x:xs) (x:ys) = True
test _ _ = False
This should check if both lists begin with exactly the same element.
But this does not work.
My compiler says: Conflicting definitions for x
I thought a pattern matching like this had to work in a functional language. I just worked with Prolog before and I'm pretty sure it worked there :/
Is this not implemented in Haskell or is my Syntax wrong?
You probably wants something like that.
test :: String -> String -> Bool
test (x:xs) (y:ys) = x == y
test _ _ = False
As #TikhonJelvis noticed, haskell is not a Prolog, so you can't check the equality of the variables inside pattern matching.
Pattern matching doesn't unify variables.
test :: String -> String -> Bool
test (x:xs) (y:ys) = x == y
test _ _ = False
So you can test each variable for equality separately, as above.