Hacker Newsnew | past | comments | ask | show | jobs | submitlogin

It's not unreasonable to dislike coding in s-expression syntax. It is not very readable.

There's a reason the vast majority of programming languages (especially weighted by popularity) use more traditional syntax.



> It is not very readable.

That holds true only for two cases:

- For a programmer who never learned Lisp as their first language. I have met people who learned Clojure as their very first PL and they said it was fun. Later there were utterly confused about Java, Python and Javascript. Going the opposite may feel confusing and identity-breaking.

- Reading static code. In a sense, it can be a bit harder to read a wall of Lisp, say printed on paper. Lispers typically don't inspect "dead code" like that; they'd connect to the live REPL and eval expressions on the go, programming it from "inside out". With experience, it becomes easier to scan the code and mentally parse it. Lisp at that point actually gets far more readable than any other PL. For instance, Lisp code is better suited for smaller screens of smartphones - the code wraps around yet retains its readability. Try that trick with literally any other language, I can 100% guarantee - most of them would look like a huge pile of indecipherable mess.


> For a programmer who never learned Lisp as their first language

Maybe. But I have never heard anyone say that Python is hard to read, and it's one of the most common complaints against Lisps. Just looking at them both it's hard to imagine how one could seriously believe that s-expressions are more readable. `(== a b)` is clearly worse than `a == b`. Even JavaScript programmers know that.

> they'd connect to the live REPL

Yeah I dunno this is the same cop-out Ruby programmers use to justify its lack of static typing. It's fundamentally better if you can understand code without having to run it.


> `(== a b)` is clearly worse than `a == b`

It's clearly worse just because it moved from infix to prefix and is wrapped by parens? Is `(* (+ a b) (+ c d))` clearly worse than `(a + b) * (c + d);`? Both have a bunch of parens, and one even has a semi colon.

This works both ways. `(list 1 2 3)` is clearly better than:

        var l = new List();
        l.add(1);
        l.add(2);
        l.add(3);
It's also better than `var l = [1, 2, 3];`

How often are you trying to make sense of a bunch of infix arithmetic operations when you're programming? Separately, how often are you creating data structures, navigating data structures, handling data in the form of JSON or XML, parsing that data into your language's native data structures, etc.?

Reading arithmetic in prefix instead of infix is easy, even if it is counter to how you were taught in elementary school. Working with s-expressions for code and data is clearly better than whatever syntax your language uses for code and either directly instantiating data or reaching for JSON or XML.

> justify its lack of static typing

Racket has both Typed/Racket as well as contracts.


> Is `(* (+ a b) (+ c d))` clearly worse than `(a + b) * (c + d);`?

Yes.

> `(list 1 2 3)` is clearly better than ...

It's not better than `[1, 2, 3]` is it?

> How often are you trying to make sense of a bunch of infix arithmetic operations when you're programming?

Very often??

Anyway it isn't just the lack of infix that makes it difficult to read - there's also the crazy bracket matching, and the lack of syntax in general. Yes that is a strength when writing parsers, macros and so on, but it also definitely hurts readability.


> It's not better than `[1, 2, 3]` is it?

If you want to change your vector to a linked list, in Lisp, you can change from `(vector 1 2 3)` to `(list 1 2 3)`. If you have some array `[1, 2, 3]` and you want to change to a linked list for whatever performance concern, you'd have to replace `[1, 2, 3]` with..

    var list = new List();
    l.insert(1);
    l.insert(2);
    l.insert(3);
Maybe this example is contrived, but I feel like it is much more of a realistic example to want to change from an unsorted map to a sorted map. You can't just simply switch from `{k1: v1, k2: v2}` to `sorted{k1: v1, k2: v2}` as you could do in Lisp from `(unsorted-map k1 v1 k2 v2)` to `(sorted-map k1 v1 k2 v2)`. You'd need to write out all of your operations as with the list example. And, all of a sudden you are stuck with using the unsorted data structure for your JSON serialization rather than having the ability to reach for a sorted data structure.

`(date 2026 6 1)` is better than "2026-06-01" because the latter isn't a date, it's a date string. `(date 2026 6 1)` is better than `new Date(2026, 6, 1);` because the former is how it is serialized and can be deserialized.

> there's also the crazy bracket matching

At least with reading code, there is almost no reason to try to match brackets at all. It's like complaining about having to read semi-colons in languages that use them to signify the end of a statement. When writing code, Lisp is just another language like all the rest that benefit from an IDE that is syntax-aware. Having highlights for the starting paren and ending paren for an expression and being able to just select a particular expression make bracket matching fairly effortless.


you could also compare

if (a === b && b === c && c === d && d == e)

To scheme's

(= a b c d e)

JavaScript clearly has the upper hand.


> never heard anyone say that Python is hard to read

I already pre-empted that: readability tracks what you learned first and how much you've practiced, and you trying to restate the familiarity effect as if it refutes it. You're measuring familiarity, not intrinsic readability. If you ask people about less popular language, say Haskell, yeah, they'd complain about its "readability" too.

> most common complaints against Lisps

Well, they are wrong on the other side of the fence. There are thousands of Lispers who'd say exactly the opposite, that: "Lisp is by far more readable than anything else"

You're cherry picking some fictive example about syntax, well, it's not a convincing one, comparing more than just a and b, blows up quickly, innit? `a === b && b === c && c === d`, while in Lisp it remains uniform `(= a b c d)`.

Lisp just uses one rule everywhere. "One uniform rule" vs "prefix for functions, infix for some operators, with a precedence table". You ever thought about that? You think you're getting an aesthetic point for binary operator example, while disregarding a bunch of layers that scream "simplicity".

> is the same cop-out Ruby programmers use

It's not the same, you clearly speaking as someone without honest, heartfelt attempt to use any modern Lisp dialects, like Clojure, Fennel or Jank. Honestly, try using Clojure, (re)write some personal shell scripts in babashka. It's truly great, and I'm saying that as someone who has used different languages, varied in paradigms. Interactive eval is not a substitute for static checking and I never offered such stance. Not to mention the enormous amount of research and experimentation on type systems that's been done by Lisp communities.




Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: