My haskell code goes as follows :
module Lain where
let value = 0
divideBy ::(Ord a, Num a)=>a -> a -> a
divideBy _ 0 = 0
divideBy num den
| (num - den) >= 0 = do
value = value + 1
return divideBy (num-den) den
| otherwise = value
The error goes on loading the haskell Lain.hs file is :
app/Lain.hs:18:1: error:
parse error (possibly incorrect indentation or mismatched brackets)
Failed, modules loaded: none.
Not able to interpret where I am going wrong, seems to me more of a logical mistake. My code wants to print the quotient given numerator and denominator. Please help as to what is exactly my mistake. Thanks in advance.
value = value + 1 isn’t a valid statement in a do block. The only valid statements are:
A variable binding: let pattern = expression
A monadic binding: pattern <- expression
An expression that evaluates to a monadic action
However, you don’t need a do block because you don’t need monadic side effects to implement this function. Furthermore, return isn’t like return in an imperative language—it’s not a keyword that returns from the current function, but a function that creates an action that returns a value. It looks like your intent with value = value + 1 was to mutate value, but there are no mutable variables in Haskell. (There are mutable reference types such as IORef, but you don’t need them here.)
So one solution is to simply use an expression:
divideBy :: (Ord a, Num a) => a -> a -> a
divideBy _ 0 = 0
divideBy num den
| num - den >= 0 = 1 + divideBy (num - den) den
| otherwise = 0
This says exactly what it means: the quotient of num and den is 0 if den is 0; if num - den >= 0, then it’s 1 more than the quotient of num - den and den; otherwise it’s 0.
Related
Why can't Haskell perform pattern matching on Num types, without us specifying Eq as a type class?
For instance:
h :: Num a => a -> a
h 0 = -1
h x = x + 1
When compiling this function, ghci complains:
* Could not deduce (Eq a) arising from the literal `0'
from the context: Num a
bound by the type signature for:
h :: forall a. Num a => a -> a
at functions.hs:9:1-20
Possible fix:
add (Eq a) to the context of
the type signature for:
h :: forall a. Num a => a -> a
* In the pattern: 0
In an equation for `h': h 0 = - 1
|
10 | h 0 = -1
| ^
Changing the function definition as following compiles and runs perfectly:
h :: (Num a, Eq a) => a -> a
h 0 = -1
h x = x + 1
*Main> h 0
-1
*Main>
From the Haskell 2010 Report, the section entitled Informal Semantics of Pattern Matching:
Matching a numeric, character, or string literal pattern k against a value v succeeds if v == k
So when you use a literal (such as 0) as a pattern, its meaning depends upon == (a method of the Eq class).
For example, your function h
h 0 = -1
h x = x + 1
can be rewritten as
h x | x == 0 = -1
h x = x + 1
You are (implicitly) using the == method, therefore you need an Eq constraint.
There are two important observations here about how Haskell differs from a lot of other languages:
The notion of equality is not defined for all types. One cannot ask whether x == y unless the type of x and y has an Eq instance.
The set of numeric types is not fixed. A numeric literal can take on any type that has an instance of Num. You can define your own type and make it an instance of Num, and it doesn't necessarily have to also have an instance of Eq. So not all "numbers" can be compared for equality.
So it is insufficient for the context of your function h to be "a has to be a number." The context must be, more specifically, "a has to be a number with an equality test" to ensure that there is a way to check whether x is equal to 0 in order to perform the pattern match.
guys, i just started learning haskell (and to code) and i have ran into a problem that i can't figure out. So there is this exercise in which i have to present the number of solutions for a 2nd degree equation.
valid a b c = if [a,b,c] == [0,0,0] then False
else (if [a,b] == [0,0] then False
else (if a == 0 then False
else True)) --function to make sure it is a 2nd degree eq
nRaizes a b c = if valid a b c == False then "not a valid eq"
else (if (b^2 - 4 * a * c) > 0 then 2
else (if ((b^2 - 4 * a * c) == 0) then 1
else 0))
Everything looked fine to me, but when i try to load the script in GHCI i get the error message:
Could not deduce (Num [Char]) arising from the literal ‘2’
from the context (Num a, Ord a)
bound by the inferred type of
nRaizes :: (Num a, Ord a) => a -> a -> a -> [Char]
at ficha1.hs:(18,1)-(21,13)
In the expression: 2
In the expression:
(if (b * b - 4 * a * c) > 0 then
2
else
(if ((b * b - 4 * a * c) == 0) then 1 else 0))
In the expression:
if valid a b c == False then
"not a valid eq"
else
(if (b * b - 4 * a * c) > 0 then
2
else
(if ((b * b - 4 * a * c) == 0) then 1 else 0))
Failed, modules loaded: none.
Can someone explain to me what is wrong with this code? And how can i fix it? Thanks
As I already commented, you should always have a type signature, before even writing any actual code. First make it clear what the purpose of your code is, before actually implementing anything!
So, valid takes three numbers and checks them in some way, yielding False or True – i.e., a boolean. Hence, a valid signature would be
valid :: Int -> Int -> Int -> Bool
This would limit the arguments to machine-sized integers – fast but not overflow-safe. It could also be
valid :: Integer -> Integer -> Integer -> Bool
or, for floating-point real numbers,
valid :: Double -> Double -> Double -> Bool
In fact, you don't need to settle on a particular type: it can be any number type, it just needs to support equality comparison. The “correct” signature would be
valid :: (Num a, Eq a) => a -> a -> a -> Bool
That's indeed also what GHC infers if you just give it the code without a type signature:
Prelude> :t valid
valid :: (Eq a, Num a) => a -> a -> a -> Bool
But the compiler can only get this right by itself because the function valid happens to be type-correct. If you put in some mistake, then the compiler has no idea what the type should be, and hence likely infer some nonsensical type that leads to a cryptic error message. (This is only one of the reasons why you should write the signature first.)
That's what happened in nraized. This also takes three numbers and gives one number. Let's keep it simple:
valid :: Double -> Double -> Double -> Int
That should certainly be ok (though you can certainly make it more generic).
Now the error message is much clearer:
<interactive>:16:87:
Couldn't match expected type ‘Int’ with actual type ‘[Char]’
In the expression: "not a valid eq"
In the expression:
if valid a b c == False then
"not a valid eq"
else
(if (b ^ 2 - 4 * a * c) > 0 then
2
else
(if ((b ^ 2 - 4 * a * c) == 0) then 1 else 0))
What this tells you is that "not a valid eq" is incompatible with the type Int. Pretty obvious actually, isn't it? A function that's supposed to return 0, 1 or 2 shouldn't be able to return a string!
If you really want this to be an error case, you should mark it as such:
nRaizes a b c = if valid a b c == False then error "not a valid eq"
...
Here, the string is not a result: if that case is encountered, the program will simply be aborted and the error message prompted at the user, instead of trying to pass it on to further functions (which couldn't possibly give meaningful results anymore, just yet stranger errors).
A couple of stylistic notes
Generally avoid nesting if with explicit mention of True and False – this is needlessly complicated: comparisons yield booleans anyway. valid just gives false if any of the equalities hold; this could be written
valid a b c = if [a,b,c] == [0,0,0]
|| [a,b] == [0,0]
|| a == 0
then False
else True
...but that's just the same as
valid a b c = not ([a,b,c] == [0,0,0] || [a,b] == [0,0] || a == 0)
or indeed
valid a b c = [a,b,c] /= [0,0,0] && [a,b] /= [0,0] && a /= 0
Anyway, these checks are heavily redundant. If a is not 0 then the list equalities can't possibly hold either! So,
valid a b c = a /= 0
would work just as well. Actually you're not even using the b and c argument, so just write
valid a _ _ = a /= 0
...or just don't define valid by itself at all: simply inline the condition a /= 0.
nRaizes a b c = if (a /= 0) == False then error "not a valid eq"
...
which is of course again completely roundabout: simply use
nRaizes a b c = if a == 0 then error "not a valid eq"
...
That still leaves you with some ugly nested ifs in nasty nested parens. Haskellers don't like that, the preferred style is to use guards:
nRaizes a b c
| a == 0 = error "not a valid eq"
| b^2 - 4*a*c > 0 = 2
| b^2 - 4*a*c == 0 = 1
| otherwise = 0
Still not optimal: you're computing the discriminant twice. Why not:
nRaizes a b c
| a == 0 = error "not a valid eq"
| d > 0 = 2
| d == 0 = 1
| otherwise = 0
where d = b^2 - 4*a*c
While error can be used like that, I wonder why you check this anyway at that point. If a==0 then it's not really a second-order polynomial, but so what? It still has a number of solutions. Really the error case should probably if all the coefficients are zero (because the number of solutions would be infinite). Hence I think the code you really want is probably the following:
nRaizes :: (Eq a, Floating a) => a -> a -> a -> Int
nRaizes a b c
| all (==0) [a,b,c] = error "Equation has infinite solutions"
| d > 0 = 2
| d == 0 = 1
| otherwise = 0
where d = b^2 - 4*a*c
Was reading monadplus chapter of haskell wiki book: https://en.wikibooks.org/wiki/Haskell/MonadPlus
digit :: Int -> String -> Maybe Int
digit i s | i > 9 || i < 0 = Nothing
| otherwise = do
let (c:_) = s
if [c] == show i then Just i else Nothing
"The do-block assures that any failed pattern match will result in returning Nothing."
However, when I tried digit 1 "", it produces irrefutable runtime error, instead of "Nothing".
I can get around it using (c:_) <- return s. It would be great if someone more experienced in haskell could confirm/clarify on this.
The code in wikibooks does not account for the case when the input string is empty. When the line let (c:_) = s is executed and s is empty, it will cause a failure in the pattern matching and an exception will be thrown. Your suggestion (c:_) <- return s is actually quite similar to the one used, except for one difference; when the pattern matching in a monadic bind (i.e. <-) fails, then the fail method of the monad will be called. Now, in the Maybe monad, fail is defined to always return Nothing,so it will cause the whole do block to return Nothing. One thing I don't like about using your suggestion is that I personally don't consider using fail to be the most elegant solution and I would prefer to use a case expression in the case:
digit :: Int -> String -> Maybe Int
digit i s | i > 9 || i < 0 = Nothing
| otherwise =
case s of
c:_ | [c] == show i -> Just i
_ -> Nothing
In fact, as you can see, we don't need to use a do block at all.
Finally, here's a more compact version of the above code:
digit :: Int -> String -> Maybe Int
digit i s | 0 <= i, i <= 9, c:_ <- s, [c] == show i = Just i
| otherwise = Nothing
This is my code so far:
test n p
|p > n = 0
|p == n = 1
|otherwise = sum [test n-p q|q<-[1..p+1]]
This should implement a simple recursive function (accepting nonnegative integers)
However I do get an error message that I do not understand. (I was not able to copy it from the ghci console, so here I just typed it out) Can anyone tell me what is wrong here?
Expected a constraint, but 'Int' has kind '*'
In the type signature for 'test': test :: Int -> Int => Int
sum [test n-p q|q<-[1..p+1]]
Function application has a very high precedence in Haskell. The above is parsed as:
sum [ (test n) - (p q) |q<-[1..p+1]]
Above test is used as a unary function returning a number, and p is also used as a unary function returning a number. This triggers a type error.
Also, note that the => is wrong in the type signature:
test :: Int -> Int => Int
-- ^^^^
The above causes GHC to try parsing the left part Int -> Int as if it were a class constraint, but it is a type ("has kind *", in technical terms) so an error is reported.
test n p
|p > n = 0
|p == n = 1
|otherwise = sum [test (n-p) q|q<-[1..p+1]]
I.e. parentheses around (n-p)
So I'm writing a program which returns a procedure for some given arithmetic problem, so I wanted to instance a couple of functions to Show so that I can print the same expression I evaluate when I test. The trouble is that the given code matches (-) to the first line when it should fall to the second.
{-# OPTIONS_GHC -XFlexibleInstances #-}
instance Show (t -> t-> t) where
show (+) = "plus"
show (-) = "minus"
main = print [(+),(-)]
returns
[plus,plus]
Am I just committing a mortal sin printing functions in the first place or is there some way I can get it to match properly?
edit:I realise I am getting the following warning:
Warning: Pattern match(es) are overlapped
In the definition of `show': show - = ...
I still don't know why it overlaps, or how to stop it.
As sepp2k and MtnViewMark said, you can't pattern match on the value of identifiers, only on constructors and, in some cases, implicit equality checks. So, your instance is binding any argument to the identifier, in the process shadowing the external definition of (+). Unfortunately, this means that what you're trying to do won't and can't ever work.
A typical solution to what you want to accomplish is to define an "arithmetic expression" algebraic data type, with an appropriate show instance. Note that you can make your expression type itself an instance of Num, with numeric literals wrapped in a "Literal" constructor, and operations like (+) returning their arguments combined with a constructor for the operation. Here's a quick, incomplete example:
data Expression a = Literal a
| Sum (Expression a) (Expression a)
| Product (Expression a) (Expression a)
deriving (Eq, Ord, Show)
instance (Num a) => Num (Expression a) where
x + y = Sum x y
x * y = Product x y
fromInteger x = Literal (fromInteger x)
evaluate (Literal x) = x
evaluate (Sum x y) = evaluate x + evaluate y
evaluate (Product x y) = evaluate x * evaluate y
integer :: Integer
integer = (1 + 2) * 3 + 4
expr :: Expression Integer
expr = (1 + 2) * 3 + 4
Trying it out in GHCi:
> integer
13
> evaluate expr
13
> expr
Sum (Product (Sum (Literal 1) (Literal 2)) (Literal 3)) (Literal 4)
Here's a way to think about this. Consider:
answer = 42
magic = 3
specialName :: Int -> String
specialName answer = "the answer to the ultimate question"
specialName magic = "the magic number"
specialName x = "just plain ol' " ++ show x
Can you see why this won't work? answer in the pattern match is a variable, distinct from answer at the outer scope. So instead, you'd have to write this like:
answer = 42
magic = 3
specialName :: Int -> String
specialName x | x == answer = "the answer to the ultimate question"
specialName x | x == magic = "the magic number"
specialName x = "just plain ol' " ++ show x
In fact, this is just what is going on when you write constants in a pattern. That is:
digitName :: Bool -> String
digitName 0 = "zero"
digitName 1 = "one"
digitName _ = "math is hard"
gets converted by the compiler to something equivalent to:
digitName :: Bool -> String
digitName x | x == 0 = "zero"
digitName x | x == 1 = "one"
digitName _ = "math is hard"
Since you want to match against the function bound to (+) rather than just bind anything to the symbol (+), you'd need to write your code as:
instance Show (t -> t-> t) where
show f | f == (+) = "plus"
show f | f == (-) = "minus"
But, this would require that functions were comparable for equality. And that is an undecidable problem in general.
You might counter that you are just asking the run-time system to compare function pointers, but at the language level, the Haskell programmer doesn't have access to pointers. In other words, you can't manipulate references to values in Haskell(*), only values themselves. This is the purity of Haskell, and gains referential transparency.
(*) MVars and other such objects in the IO monad are another matter, but their existence doesn't invalidate the point.
It overlaps because it treats (+) simply as a variable, meaning on the RHS the identifier + will be bound to the function you called show on.
There is no way to pattern match on functions the way you want.
Solved it myself with a mega hack.
instance (Num t) => Show (t -> t-> t) where
show op =
case (op 6 2) of
8 -> "plus"
4 -> "minus"
12 -> "times"
3 -> "divided"