1. 20
  1. 4

    M-expressions are just.. ugly. Though I’m surprised the mathematical notation is not more common.

    This is just gorgeous: x ↦ x*x I wonder why no programming language uses it.. It beats scrap out of haskell’s \x -> x*x -thing.

    1. 7

      I wonder why no programming language uses it

      …because it’s not particularly easy to type “” I think is the obvious answer. As far as I understand the backslash in Haskell’s lambda syntax is meant to resemble a lambda symbol, so as to approximate a lambda calculus term, and you can also get closer to the example you’ve highlighted using a font with ligatures like Hasklig.

      I think syntax using these kinds of special characters is more common in Agda as well, e.g. https://github.com/copumpkin/categories/blob/00e385d442073c2343145cfefa58dae63d58877e/Categories/Functor/Product.agda#L52h (random example I found by searching through github).

      1. 4

        Church is reported to have intended to use ^ rendered as e.g. x̂ or ŷ but the typesetter couldn’t manage it and wrote ^x instead. The story goes that looked enough like λ that influenced the next typesetter to try something else…

      2. 1

        Agda has support for some special characters.

        Some examples: https://plfa.github.io/Lambda/

        1. 1

          k/q uses M-expressions, but allows operators to be used infix, so:

          set[`square;{[n] *[n;n]}]
          

          can also be written as:

          square:{[n] n*n}
          

          But a really cool trick is to observe “x” is the default first value:

          square:{x*x}
          

          which is hard to beat!

          APL (specifically Dyalog) also deserves some note. It doesn’t use M-expressions, uses ← for assignment instead of colon, and ⍵ as the right-hand argument, which is the same in some ways, but perhaps a little more beautiful:

          square←{⍵×⍵}
          
          1. 1

            I don’t like JS, but lambda arrows remembers this perfectly.

          2. 3

            It reminds me of Mathematica’s syntax.

            1. 3

              IIRC, that’s because Mathematica very deliberately tried to “finish” the work on M-expressions and use it for its syntax, but I can’t find a reference to that at the moment, so I might be wrong.

              1. 1

                It sounds right. Mathematica is Lisp with M-expressions, in many ways.

            2. 1

              The article mentions I-expressions as a later attempt to make a mathier Lisp syntax. An even more recent attempt is “sweet-expressions”, which adds more traditional syntax for nesting (with indentation), function calls, and infix expressions. For example, these S-expressions:

              (let* ((x 1)
                     (y (+ x 1)))
                (list y x))
              

              could be written as these sweet-expressions:

              let*
                \\
                  x 1
                  y {x + 1}
                list(y x)
              

              I once looked into porting sweet-expressions for use with Clojure. Sadly, Clojure has optimized its forms to be easy to write in S-expressions by removing nested lists where possible. This means that sweet-expressions’ indentation rules, which are optimized for the high amount of nesting in Scheme forms, are not very useful for writing Clojure. Clojure’s significant brackets ()/[]/{} reduce the usefulness of indentation rules too, and make it impossible to use {} for infix as sweet-expressions do.