views:

162

answers:

3

I am trying to compile this example in mono on ubuntu.

However I get the error

wingsit@wingsit-laptop:~/MyFS/kitty$ fsc.exe -o kitty.exe  kittyAst.fs kittyParser.fs kittyLexer.fs main.fs 
Microsoft (R) F# 2.0 Compiler build 2.0.0.0
Copyright (c) Microsoft Corporation. All Rights Reserved.

/home/wingsit/MyFS/kitty/kittyAst.fs(1,1): error FS0222: Files in libraries or multiple-file applications must begin with a namespace or module declaration, e.g. 'namespace SomeNamespace.SubNamespace' or 'module SomeNamespace.SomeModule'

/home/wingsit/MyFS/kitty/kittyParser.fs(2,1): error FS0222: Files in libraries or multiple-file applications must begin with a namespace or module declaration, e.g. 'namespace SomeNamespace.SubNamespace' or 'module SomeNamespace.SomeModule'

/home/wingsit/MyFS/kitty/kittyLexer.fsl(2,1): error FS0222: Files in libraries or multiple-file applications must begin with a namespace or module declaration, e.g. 'namespace SomeNamespace.SubNamespace' or 'module SomeNamespace.SomeModule'
wingsit@wingsit-laptop:~/MyFS/kitty$ 

I am a newbie in F#. Is there something obvious I miss?

A: 

This problem arises because those sample files were written for a version of F# that didn't have that requirement.

As the error message explains, all you need to do is to add namespace SomeNamespace to the top of each file, and it will compile just fine. Even in mono on ubuntu.

sblom
+2  A: 

You can probably fix it up by adding

module theCurrentFileName

to the top of each .fs file.

Indeed, this is a newer requirement, and the sample is old and needs updating.

Brian
+3  A: 

As Brian and Scott pointed out, you need to enclose the file in a namespace or module declaration. Just adding namespace SomeNamespace may not work if you have top-level let binding in the file (as these must be in some module). The following would be invalid:

namespace SomeNamespace
let foo a b = a + b   // Top-level functions not allowed in a namespace

That said, I prefer having namespace instead of module at the top-level and then wrapping all functions in a module explicitly (as I believe that makes code more readable):

namespace SomeNamespace
module FooFunctions =     
  let foo a b = a + b

But of course, you can add top-level module as Brian suggests (earlier versions of F# automatically used the name of the file in PascalCase as the name of top-level module used in the file):

// 'main.fs' would be compiled as:
module Main
let foo a b = a + b
Tomas Petricek