Q:

Haskell if then else with "two statements"

How can I do this:
if n > 0
then putStrLn "Hello"
     putStrLn "Anything"

I want to have "two statements" in one condition but I keep getting compilation errors
I tried using semi-colon with no luck

A:

then can only take one value....  But you are in luck, because do smashes multiple IO() values into one....
if n > 0
  then do
    putStrLn "Hello"
    putStrLn "Anything"
  else return ()

Remember, in Haskell, you need an else also (and return () creates the trivial IO() that does nothing).

A:

Your example wouldn't make sense in Haskell. Every expression needs to have a value, which is why you always need to have an else, even if it is just return ().
Because it needs to be a single expression, you can't just do
putStrLn "Hello"
putStrLn "Anything"

since those are two expressions of type IO (), which means it is a computatinon with some external effects, and that there is no result. You have two computations that need to run in a sequence, which can be done using the >> combinator
putStrLn "Hello" >> putStrLn "Anything"

There is also an alternative syntax using the do block.
do
  putStrLn "Hello"
  putStrLn "Anything"

The important thing to note here is that this will compile to the same >> code as the example above. The do block can be thought of just as syntactic sugar (there is more to it, but for simplicity you can think of it that way.)
Putting this all together leaves us with
if n > 0
then putStrLn "Hello" >> putStrLn "Anything"
else return ()

or using the do block
if n > 0
then do
  putStrLn "Hello"
  putStrLn "Anything"
else return ()

Because this pattern is quite common, there is a when combinator (in Control.Monad), which does precisely this
when (n > 0)
  do
    putStrLn "Hello"
    putStrLn "Anything"

or just simply
when (n > 0) (putStrLn "Hello" >> putStrLn "Anything")

