tibbe / haskell-style-guide

A style guide for Haskell code.
957 stars 75 forks source link

if-statements #5

Closed ghost closed 12 years ago

ghost commented 12 years ago

How should I indent if-statements? How should I indent them in do-blocks?

pmsorhaindo commented 12 years ago

This works everytime for me. The key (for me anyway) is the then and the else at the same level of indentation. Especially guaranteed to work if you just make the then and else statements one function as you can then be sure nothing funny is happening indentation wise.


if (booleanExpression)
    then trueFunction x y
    else falseFuntion x y
ghost commented 12 years ago

Unfortunately, in do-blocks, this indentation is illegal according to Haskell98, as far as I know. If I understand correctly, the purpose of this Haskell'-ticket http://hackage.haskell.org/trac/haskell-prime/wiki/DoAndIfThenElse is to make it legal. Howbeit. HLint prints an error with the following code:

foo = do
  if condition
  then doThis
  else doThat

Personally, I prefer this layout which is illegal as well:

foo = do
  if   condition
  then doThis
  else doThat

Other people use

foo = do
  if condition
     then doThis
     else doThat

while some other like to indent as much as possible with two whitespaces like this:

foo = do
  if condition
    then doThis
    else doThat

And even this layout is used for simple and short conditions:

foo = do
  if condition then
      doThis
  else
      doThat

which is illegal as shown by the link above.

So, I'm desperate. Which layout should I use (for IF-statements in DO-blocks)?

pmsorhaindo commented 12 years ago

By illegal do you mean, stuff won't compile. Or are you just worried about style?

Sorry I forgot code block.

ghost commented 12 years ago

it's simply (or was?) not allowed. so, the compilers actually shouldn't compile it. i'm not sure, actually. at least, it compiles fine in current GHCs. but HLint still says it's invalid.

pmsorhaindo commented 12 years ago

As far as I know any except the first two representations you've shown should consistently compile. Just don't use tabs.

jaspervdj commented 12 years ago

My 50 cents, to maintain consistency with the rest of the style guide (4-space indent), and compatibility with older GHC versions, I think this should be the preferred formatting:

foo = do
    someCode
    if condition
        then doThis
        else doThat

If I correctly understand the case, someCode is always present, if it is not, you should probably use guards?

Here is a longer example -- note how I maintain 4-space indenting, even in the nested do blocks.

Additionally, I think that one should be allowed to format it on a single line (if line length is not greater than 80 columns):

foo = do
    someCode
    if condition then doThis else doThat

Naturally, guards and pattern matches should be preferred over if-clauses, whenever possible.

ghost commented 12 years ago

I agree. That's a nice suggestion.

pmsorhaindo commented 12 years ago

I definitely prefer that. I'd imagine quite a few one-liner if-else's could become guards

tibbe commented 12 years ago

I do what @jaspervdj said. It's consistent with how we align expressions in general. Is it worth writing down?

jaspervdj commented 12 years ago

It think it's worth mentioning -- I've seen some weirdly formatted if-clauses in the wild. I'll rewrite my reply a bit and drop you a pull request.

tibbe commented 12 years ago

Sounds good. In addition to your examples perhaps it's worth noting that

f = if ...
    then ...
    else ...

is also fine in expression contexts (just as you could format any other expression like that.)

tibbe commented 12 years ago

Fixed in 6999aa020c776fd265aa269bd951dcc666bb0ea7 and 744e395c725a094c2c13b08a85db3015a7c16139.