I’m studying Chapter Input and Output in the book Learn You a Haskell For Great Good. I try to have a basic understanding of why I/O actions will only be performed when they are given a name of main.
To my experience, in Haskell we use = to declare function name and define the function body.
So in my point of view,
main = putStrLn "I like you."
is just a “const” function takes no input and returns a term of type “IO ()”, where IO here is a type constructor IO :: * -> * and according to the text, () is the unit type also a concrete type. So I think the name main is changable. And I declare main' as follows :
-- main = putStrLn "I like you."
main' :: IO ()
main' = putStrLn "I like you."
Unfortunatly, Haskell warns me that the I/O action is not defined. This looks confused to me, since in GHCI I’m allowed to do the following things :
λ> main = putStrLn "I like you."
λ> main
I like you.
λ> main' = putStrLn "I like you."
λ> main'
I like you.
I don’t know why main and main' behave so different outside of the GHCI prompt!
The error message is very confusing. When you call GHC on a file without a module name, then it defaults to Main which must have a main function.
You can write your custom main' function in a file and have it compile properly, but then you have to give your module another name. For example you can write this:
module Foo where
main' = putStrLn "I like you"
This compiles without errors (but it does not produce an executable because there is no entrypoint).
Oh! I see the problem! It seems like Emacs’s Haskell-mode automatically import some modules for me which cause the warning.
BTW thanks for explaining the process! I think I understand better now!