Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Multiple source files in Haskell

I'm writing my first big project in Haskell and I'd like to split it across multiple files. So far, I have written two modules, Parse and Eval. I'd like to have a Main module that just includes these two modules and specifies the main function. I have the files Main.hs, Parse.hs, and Eval.hs and import them in Main, but this happens:

Prelude> :load "~/code/haskell/lisp/Main.hs"
[1 of 3] Compiling Eval             ( Eval.hs, interpreted )
[2 of 3] Compiling Parse            ( Parse.hs, interpreted )
[3 of 3] Compiling Main             ( ~/code/haskell/lisp/Main.hs, interpreted )
Ok, modules loaded: Main, Parse, Eval.
*Main> parse parseExpr "" "#b101"

<interactive>:1:0: Not in scope: `parse'

The parse function comes from Parsec library, which is imported in Parse.hs. What's wrong?

like image 323
Igor Avatar asked Aug 19 '10 16:08

Igor


People also ask

How do I load HS files in Haskell?

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.)

How do I run a ghci file?

GHCi is the interactive interface to GHC. From the command line, enter "ghci" (or "ghci -W") followed by an optional filename to load. Note: We recommend using "ghci -W", which tells GHC to output useful warning messages in more situations. These warnings help to avoid common programming errors.

How do I load a Haskell file in Terminal?

If you have installed the Haskell Platform, open a terminal and type ghci (the name of the executable of the GHC interpreter) at the command prompt. Alternatively, if you are on Windows, you may choose WinGHCi in the Start menu. And you are presented with a prompt. The Haskell system now attentively awaits your input.

How do I load a module in Haskell?

The syntax for importing modules in a Haskell script is import <module name>. This must be done before defining any functions, so imports are usually done at the top of the file. One script can, of course, import several modules. Just put each import statement into a separate line.


2 Answers

From the Haskell report:

A module implementation may only export an entity that it declares, or that it imports from some other module. If the export list is omitted, all values, types and classes defined in the module are exported, but not those that are imported.

You either need to give an explicit export list that includes parse in Parse.hs, or import parse again in your Main.hs.

like image 128
Travis Brown Avatar answered Oct 07 '22 22:10

Travis Brown


You can also do this:

module Parse (parse) where
    import qualified Text.ParserCombinators.Parsec as P

    parse = P.parse

But really, this is useless. You'll certainly be wanting to build something more domain-specific on top of Parsec before you export it from one of your modules.

like image 30
Michael Melanson Avatar answered Oct 08 '22 00:10

Michael Melanson