Do you always add a trailing comma?

Yeah, foo bar 1 is foo(bar(1)) or foo(bar, 1)?

1 Like

Well, my comment might have been a bit tongue-in-cheek :smiley: but obviously you’d use parentheses to remove ambiguities .

[(blah 1 2) 3 4]

In elixir you have this problem today don’t you, because optional parenthesis?

foo bar 1, 2, 3

No in elixir. Yes in javascript.

I like it when elixir yell at me when I run mix. I do not like it when javascript yell at me, I also like to tell myself I know javascript long enough to handle whatever happen by adding trailing comma if something were to occur.

Why do you think people don’t mind extra commas but want parenthesis to be optional?

Easy from the Clojure perspective: (foo bar 1) is equivalent to Elixir’s foo(bar, 1). (foo (bar (1))) would be foo(bar([1])).

In Clojure, , is treated as whitespace, exactly the same as spaces, tabs, or newlines.

2 Likes

I always use parens in function calls. In my opinion, eliding parens should ONLY be used for macro invocations that extend syntax in such a way that parens would be awkward.

5 Likes

Beats me :smiley: We are irrational human beings.

Probably because syntax is hard. And the more syntax you add, the more compromises and unintended side-effects you get as well.

From my point of view I find the syntax without parenthesis but with commas hard to mentally parse.

# In order of preference I think

# ML style looks good to me
let foo a b c = (a + b) * c
...
foo 1 2 3

# Lisp style looks good
(defun foo (a b c) (* c (+ a b)))
...
(foo 1 2 3)

# Elixr with parens
def foo(a, b, c) do
    (a + b) * c;
end
foo(a, b, c)

# But elixir style without parens?
def foo a, b, c do
   (a + b) * c
end
...
foo a, b , c

# with the optional brackets I have an even harder time
foo a, b, a: 1, b: 2, c: 3

To get back to the topic. Do I prefer trailing comma? I understand it makes refactoring and moving things around slightly easier but code looks more pleasant without it.

1 Like

code looks more pleasant without it

That’s highly subjective. I am of the opposite opinion personally.

4 Likes

Yes of course. I never meant my reply to be authoritative. Perhaps I should have phrased it: “In my opinion the code look more pleasant without it.”

1 Like

I don’t add trailing because back in the days I spent lots of hours tracking a bug which was only due one of these (PHP or JS I don’t remember which of these jewels).

Now I don’t ask myself if I wan’t them or not, I have formatters (or at least syle guide) for all languages!

Umm - should you terminate English sentences with a comma instead of a period, in case you want to reorder the sub-clauses,

No, I don’t like this,

:slight_smile:

2 Likes

I find no trailing comma to be better readable. About the reordering / diffing argument I kinda feel like that could also be solved by more intelligent editors/diffing algorithms and mustn’t be done by me adding more commas.

3 Likes

English isn’t programming. Heck english isn’t even nicely parseable in any way. ^.^

It is more akin to each statement being ended with a period in English. ^.^

I find it less readable as it is a weird discontinuity:

[
  Something.longCall(1, 2, andmore()),
  Blah.blorp("hello", "world"),
  Breep.gorp(6.28, 42)
]

Compared to the thing that actually follows the same pattern on every line:

[
  Something.longCall(1, 2, andmore()),
  Blah.blorp("hello", "world"),
  Breep.gorp(6.28, 42),
]

No weird discontinuities there. :slight_smile:

3 Likes

Sure there is - there’s a comma and nothing that follows; feels like something is missing (or was forgotten). No comma means I’m done; comma implies there is more to come.

Sure there is, the end tag of the list ] follows it. :slight_smile:

To me a comma at the end of an item means that item is ‘terminated’ in the listing. It is a separator when used on a single line, a terminator when on multi-line.

This is like in OCaml, do you do a prefix | or not? I.E. would you do a match like this:

match blah with
  1 -> "1"
| 2 -> "2"
| 3 -> "3"
| _ -> "?"

Or would you do it like this?

match blah with
| 1 -> "1"
| 2 -> "2"
| 3 -> "3"
| _ -> "?"

The | is a case separator, it technically should not be before the first one, you can even write it like this just fine either way:

match blah with 1 -> "1" | 2 -> "2" | 3 -> "3" | _ -> "?"

match blah with | 1 -> "1" | 2 -> "2" | 3 -> "3" | _ -> "?"

Yet most people will write it with a prefix | on the first one when multiline and without a prefix | on a single line. Same thing when writing , on the last line in a list of elements as well, or rather a ; is a list separator in OCaml:

(* Single line *)
let some_list = [1; 2; 3; 4]

(* Multi line *)
let some_list = [
  1;
  2;
  3;
]

You can of course do it backwards if you so wish though I rarely see this done:

(* Single line *)
let some_list = [1; 2; 3; 4;]

(* Multi line *)
let some_list = [
  1;
  2;
  3
]
4 Likes

That seems revisionary to justify trailing commas.

A comma either

  • separates two adjacent items that could be otherwise mistaken as being one or
  • joins two obviously distinct adjacent items into one structured whole

Trailing commas are a fairly recent thing.

The version control system excuse is just another case of DX winning over UX - lets not bother dealing with this in the diffing logic (and the few developers dealing with it) but rather download this to millions of users of the version control system by adjusting their habits and forcing programming languages to alter the semantics of punctuation characters.

As much as some people may hate the idea of leading commas - at least that is a self-contained solution that doesn’t impose responsibilities elsewhere.

1 Like

I find that level of strictness off-putting and needlessly nitpicky. Programming languages, editors, IDEs and tooling are meant to serve the humans, not the opposite.

1 Like

This can be a little bit of the problem, for the same reason why by default all changes in whitespaces also are present in Git diffs. The reason for that is that you can send output of git diff (the default one) to the other person and this is perfectly valid diff which that person can apply that diff using standard tools, with requiring the default diff tools to omit commas it could result in incorrect diffs (as commas are required by the syntax in most languages, while whitespaces aren’t).

2 Likes

You could just as easily separate using whitespace and disambiguate via parenthesis as well.

But still, this is not the only time this pattern has popped up (and a trailing comma I know was accepted in at least fortran (and later modula-3, which also had an optional leading | too) back when I was a child, so it’s quite a few decades old pattern at this point). One big thing is semicolons. In just about any older language that use a semicolon as a statement separator (*cough*C*cough*, and erlang uses semicolons too!) they did not allow trailing semicolons. Eventually C when standardized accepted the extra odd semicolon without giving you a syntax error (it just ignored it until finally the standardization required it).

Thus following the idea that ‘because they separate items’ then there should be no trailing comma also states that ‘because they separate statements’ then there should be no trailing semicolons. Do you subscribe to this as well or do you think it is special cased for some reason in a way that lists are not? :slight_smile:

Exactly this. This is why the trailing semicolon was eventually accepted as ‘human noise’ by most languages (not all, look at most ML languages!), because it helps the human even though it is noise to the compiler.

6 Likes

I would argue that nothing is also some kind of statement.

2 Likes