I'm new to Haskell and after starting ghci I tried:
f x = 2 * x
and I obtained:
<interactive>:1:4: parse error on input `='
which I don't understand.
Strangely, it worked well before. I suppose that I have done misconfigured Haskell. Reinstalling ghc6 doesn't solve the problem.
For information, I use Ubuntu 10.4 and the version of ghc6 is 6.12.1-12
In GHCi 7.x or below, you need a let to define things in it.
Prelude> let f x = x * 2
Prelude> f 4
8
Starting from GHC 8.0.1, top-level bindings are supported in GHCi, so OP's code will work without change.
GHCi, version 8.0.1.20161213: http://www.haskell.org/ghc/ :? for help
Prelude> f x = x * 2
Prelude> f 4
8
When you type into a Haskell source file,
f x = 2 * x
is correct.
When you type directly into ghci, you need to type let at the start of the line:
let f x = 2 * x
A good rule of thumb for using ghci is that any code you enter should conform to do-block semantics; that is, you could assume syntactically that you're programming within the IO monad (if this is new terminology, don't worry! I'd highly recommend reading through this tutorial).
This answer illustrates this point with an example, and may provide more working insight into the nature of IO and ghci.
Starting in GHC 8.0.1 this would no longer generate an error.
Related
I am trying to declare a function in Haskell GHCi as
fact :: Int -> Int
But I am getting this error - error: parse error on input `->'
I do not understand why this is happening. Can anyone please explain it to me? Thanks.
First off, it looks like you're using a pretty old version of GHC. In newer versions, the GHCi syntax has been relaxed a bit.
But still: what you type in GHCi does not have the same rules as what you write in a Haskell source file. Specifically, the GHCi prompt is essentially an IO monad chain evaluator, the reason being that you can write stuff like
Prelude> putStrLn "Hello"
Hello
or
Prelude> readFile "test.txt"
"fubar\nbaz"
and actually have it execute right there. By contrast, in a Haskell source file, you only declare bindings, and these can then be invoked in the main action or a GHCi session.
But in this case, you want to declare a binding within GHCi itself. You can do that too, but it's a bit awkward, basically you need to start with let and then squeeze everything in a single line:
Prelude> let fact :: Int -> Int; fact n = product [1..n]
Actually, newer GHCi version allow you to omit the let, and you can have multiple-line definitions by using a special bracket syntax:
Prelude> :{
Prelude| fact :: Int -> Int
Prelude| fact n = product [1..n]
Prelude| :}
but I would recommend against this. If you actually have some bigger definitions, better put them in a proper Haskell source and load that into GHCi.
I am completely new to Haskell. I have been trying to learn how to write functions, lets say to add two integer numbers. I am currently using GHCi to code Haskell. I tried learning from http://www.haskell.org/tutorial/functions.html, however this does not work, I get a not in scope error. I greatly appreciate any help with this. Am I supposed to not use GHCi to code haskell in order to create functions? GHCi, seems to work okay so far, for everything other than functions.
Many thanks in advance.
You have to use let to declare functions in GHCI
ghci>let add x y = x + y
ghci>add 3 3
6
In general though I would advice you to open up a text editor and write your functions in there, save as .hs and open it with :l in ghci
Like this ( from RWH)
-- file: ch03/add.hs
add a b = a + b
Then:
ghci> :l add.hs
[1 of 1] Compiling Main ( add.hs, interpreted )
Ok, modules loaded: Main.
ghci> add 1 2
3
I'm beginning Haskell... I tried to write the following trivial function in two different ways, letting Haskell decide the types, and the type system does something different in each case. What is the explanation for that behavior?
Prelude> let f x = 2 * x
Prelude> let g = (2*)
Prelude> :info f
f :: Num a => a -> a -- Defined at <interactive>:1:5
Prelude> :info g
g :: Integer -> Integer -- Defined at <interactive>:1:5
Thanks!
This is known as the monomorphism restriction.
Basically, it means that top-level bindings that look like x = are forced to be non-polymorphic, unless you specify a type signature. Bindings with arguments, i.e. f x = are not affected. See the link for details as to why this restriction exists.
Usually, you get an error message when the restriction is applied, but in this case GHCi is able to use type defaulting to change the type Num a => a to Integer.
The easiest way to dodge it is to either use an explicit type signature, or put
{-# LANGUAGE NoMonomorphismRestriction #-}
at the top of your module, or run GHCi with -XNoMonomorphismRestriction.
As others have pointed out, this is caused by something called the "Monomorphism Restriction".
MR can be useful for writers of Haskell compilers, and there is controversy about whether or not it is worthwhile to have in the language in general. But there is one thing everyone agrees: at the GHCi prompt, MR is nothing but a nuisance.
MR will probably be turned off by default in this context in an upcoming version of GHC. For now, you should disable it in GHCi by creating a text file called ".ghci" in your home directory that contains a line like this:
:set -XNoMonomorphismRestriction
Because the definition of g doesn't explicitly name its arguments, you run into the monomorphism restriction, preventing g from being polymorphic and (in this case) causing GHC to default to Integer.
I'm new to functional programming. I have a basic question.
I'm using the Hugs interpreter,
I would like to write a function in Haskell; I went though several tutorials, but I'm not getting it.
fact :: Int -> Int
fact n = if n == 0 then
1
else
n * fact (n-1)
This gives me a syntax error :-S
ERROR - Syntax error in input (unexpected `=')
I assume you type this right into the interactive prompt. Sadly, these are relatively primitive in Haskell - complex definitions, such as fact, can't be entered at the prompt, at least not in the same way you'd normally write them.
You need to put function definitions etc. into modules, then load those via (e.g.) :load fact.hs. There are resources for Hugs specifically that provide more information on this and other topic (I used http://cvs.haskell.org/Hugs/pages/hugsman/index.html to check my assumptions).
Also note that indentation matters, so the code won't work the way you posted it here even when in a module. Those tutorials will have correct versions. If not, they're useless and you should forget them.
The syntax is incorrect. In Haskell, whitespace matters, much like it does in Python. More specifically, if you have text that starts on the first column of a line, the interpreter will think it's a top-level declaration. The correct syntax would be (for example):
fact :: Int -> Int
fact n = if n == 0
then 1
else n * fact (n-1)
You could also put the if in one line if you'd like to. So if you're using an interactive prompt you could do:
λ> let fact n = if n == 0 then 1 else n * fact (n-1)
Notice that you'll need to use let in order to define functions on the prompt (at least this is how it's done in GHCi, I'm not sure about Hugs). You'll be better off putting them in a separate file and then loading that in the interpreter. But anyway, a much nicer solution would use pattern-matching in my opinion anyway:
fact :: Int -> Int
fact 0 = 1
fact n = n * fact (n-1)
Here, the interpreter would pattern-match the first argument of the function against the possible cases listed. So if the first argument is null, the result if 1, otherwise apply the function recursively.
Create a file named, for example, fact.hs
-- copying cedric's nicely formatted code
fact :: Int -> Int
fact n = if n == 0
then 1
else n * fact (n-1)
That's all that really needs to be there. When you want to make real modules, you should do some extra stuff.
Now, open up ghci from the same folder. At the ghci prompt, use the :l command to load the "module"
Prelude> :l fact.hs
[1 of 1] Compiling Main ( fact.hs, interpreted )
Ok, modules loaded: Main.
*Main> fact 3
6
*Main> fact 10
3628800
I assume it's a very similar process with Hugs. I think hugs requires the file name to be capitalized. ghci simply creates a "Main" module and puts your code in it; that's why the prompt changes from Prelude> to *Main>
When I work on small Haskell functions, I usually keep two terminals open: one for vim and one for ghci. When I change the file in vim (and save it), I just use :r in ghci to reload the new definitions.
*Main> :r
Ok, modules loaded: Main.
It should be mentioned that the most elegant way to write this function is:
fac n = product [1..n]
See http://www.willamette.edu/~fruehr/haskell/evolution.html for details.
Compiling the following Haskell program with GHC 6.12.1 yields an error:
{-# LANGUAGE NoImplicitPrelude #-}
module Example where
import Prelude(Integer, fromInteger, (==))
f :: Integer -> Integer
f n
| n == 0 = 0
Namely:
example.hs:9:6: Not in scope: `>>'
The error goes away when I change the import statement to:
import Prelude(Integer, fromInteger, (==), (>>))
This makes sense. What I don't understand, however, why there is an error in the first place. My program doesn't seem to make use of any Monad, while >> is one of the Monad operators.
I don't know the root cause of this problem, but if you compile your code with -ddump-rn-trace option on, you can see that the compiler for some reason puts (>>) into a list of definitions used, something like that:
finish Dus [(Nothing, [(314, Integer)]),
(Just [(rdd, f)], [(01D, >>), (01E, fromInteger), (01L, ==)]),
(Nothing, [])]
Most certainly it is a bug in GHC 6.12.1
This is a bug in ghc. You should report it.
I can imagine the compiler checks to see if >> is present (which it needs for compilation of do-blocks), no matter if do occurs in your code.
(But then, it should also complain about >>=)