Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I use a let within a do block in ghci?

Tags:

haskell

ghci

I'm trying to create a do block interactively in ghci. As long as I don't define a variable with in block, it's fine:

Prelude>let a = do putStrLn "test"; putStrLn "other test"
Prelude>

but I can't figure out how to define a let construction in the do block interactively without getting a parse error:

Prelude> let a = do let b = 5; putStrLn $ show b

<interactive>:2:40:
    parse error (possibly incorrect indentation or mismatched brackets)

Obviously

let a = do
     let b = 5
     putStrLn $ show b

is entirely fine in a Haskell source file. I'm just having trouble figuring out how to translate that to ghci.

like image 554
Tneuktippa Avatar asked Mar 07 '13 14:03

Tneuktippa


People also ask

How do I quit GHCi?

Quits GHCi. You can also quit by typing control-D at the prompt. Attempts to reload the current target set (see :load ) if any of the modules in the set, or any dependent module, has changed. Note that this may entail loading new modules, or dropping modules which are no longer indirectly required by the target.

How do I run a program in GHCi?

Open a command window and navigate to the directory where you want to keep your Haskell source files. Run Haskell by typing ghci or ghci MyFile. hs. (The "i" in "GHCi" stands for "interactive", as opposed to compiling and producing an executable file.)

What does variable not in scope mean in Haskell?

(When GHC complains that a variable or function is "not in scope," it simply means that it has not yet seen a definition of it yet. As was mentioned before, GHC requires that variables and functions be defined before they are used.)


2 Answers

:help

 <statement>                 evaluate/run <statement>    
:{\n ..lines.. \n:}\n        multiline command

You can type :{ to start a multiline command, and type :} to end it.

So just do

 Prelude> :{
 Prelude| let a = do
 Prelude|     let b=5
 Prelude|     putStrLn $ show b
 Prelude| 
 Prelude| :} 

Be careful with layout (indentation/whitespace). Otherwise you can get parse errors in apparently correct code.

For example the following will NOT work because the indentation isn't deep enough:

Prelude> :{
Prelude| let a = do
Prelude|    let b=5
Prelude|    putStrLn $ show b
Prelude| 
Prelude| :}

It will lead to a parse error like this:

<interactive>:50:4: parse error on input ‘let’
like image 132
onemouth Avatar answered Oct 11 '22 01:10

onemouth


I landed here because I had the same question, but yatima2975's answer reminded me of how each let-block can have multiple bindings, so I tried the below and indeed it works.

$ ghci
GHCi, version 8.8.3: https://www.haskell.org/ghc/  :? for help
Prelude> do { let { x = 1; y = 2 }; putStrLn (show (x, y)) }
(1,2)
like image 22
easoncxz Avatar answered Oct 11 '22 01:10

easoncxz