Language sweet spots

I saw an interesting response on another forum that talked about language design (+ implementation?) ‘sweet spots’.

Racket hits a sweet spot for me with

  • Parenthetical syntax
  • expression based
  • TCO
  • Modules
  • contracts and run-time type checking
  • interoperability with Typed Racket so I can use the Plot library (I’m assuming I could also interoperate with datalog or mini Kanren if I wanted logic programming? I’ve never tried it)

To my shame I have not tried Haskell but I imagine the sweet spot is due to

  • compile time type-checking & inference
  • lazy evaluation
  • non-parenthetical syntax (I don’t know what to call it?)
  • (I’m sure there are many others!)

I’ll stop with those two because I only know obvious ones like c#(ecosystem,corp backing), Python(huge community, popular syntax), JavaScript(browsers)., Java etc

So my first question here is what are the factors that make Racket hit the sweet spot for you?

My second question is are there other languages that hit a sweet spot for you? And what are those factors?

Beast regards

Stephen

(My understanding of a ‘sweet spot’ is it is the best bit of the tennis racket stringy bit. The place where you get the most power and control hitting a ball.)

1 Like

I saw the post, initially, and wanted to chime in with a "Racket is great, that is all!", but I feel like that isn't very intellectually honest.

A blog post by Hillel Wayne about "toolbox languages" has recently been making the rounds on lobste.rs, and I think the description he provides, helps a lot to define what I consider to be Racket's sweet spot:

A toolbox language is a programming language that’s good at solving problems without requiring third party packages.

Basically, whenever I need to get something done, I reach for Racket. Of course, I am biased because I use Racket (almost) every day, but I do know a couple of other languages, including Java, Python, PowerShell, and recently C#; all of which I have come to appreciate in their own ways.

What differentiates Racket, I think, is that it is particularly good at applying the maxim of being "conservative in what you emit, and liberal in what you accept". It does a very good job of putting the user (me) first. It mostly stays out of my way, and when I need to change it, or I feel like I need to add a dash of special sauce, I can!

I would augment Hillel's definition slightly, to exclude the bit about "[not] requiring third party packages" because I feel like this misses a great deal of what makes Racket nice to use. To wit, a carpenter is not a [kitchen] island! The lobste.rs discussion mentions Frink and, as I suspected, there is a Racket library which does something equivalent. Running a raco pkg install ... is too convenient for me to exclude from consideration.

Obviously, in his metaphor, each language is like a tool in the box, but in this context, I feel like the ideas that glue Racket together, are in fact the real tools in the box. Anyone can use a hammer, but at some level there is also an "internal manual" that you have to consult, and examples of previous uses, to really start nailing it.[0]

He goes on to elaborate that a toolbox language should be fast to write. I have not experienced another language with the same ease-of-development that Racket fosters. As an example, in the past week I have had to write a parser for email notifications posted to an IMAP server.

The proof of concept was written in Racket, and probably took about 3 hours to complete, most of which was spent fiddling with a tricky regular expression, and came out to roughly 126 loc, including the IMAP client usage, but minus the comments.

The equivalent program in C# took quite a bit of time longer to write, purely from an implementational perspective, because the language forces me to "segregate" my thoughts much more rigidly, and it is obviously much more verbose.

Neither was "better" because the behaviour remained the same (modulo my own stupidity), but I felt less "encumbered" by the Racket solution. I also don't have to worry as much about the way my code is presented in Racket, because the syntax is so malleable. Instead of torturing my code into a specific format all my teammates have come to expect, I can lay it out however I think makes the code more readable.

Hillel also mentions a smooth on-ramp for learning the language. I think Racket shines here as well. I often feel like I am a bad programmer because I do not know a significant amount of what my language can do. This is likely true of most programmers and languages; however, I always feel like Racket is inviting me to learn more because of its great documentation and community, whereas I often feel like a "scrub" in the same context for another language.

This is more of a "social problem" I think, than it is a "language problem". There will always be a learning curve to any new information, but the trick is that the information can only do so much to become lodged in your brain. At some point, people--other people--need to be involved, and this makes all the difference.

Anyways, I think the sweet spot that Racket hits, is that it allows me to be whichever kind of programmer I want to be today.

Mooiloop!


[0] This is just a feeling; I don't have a specific idea in mind here, but I trust that it is not unfounded because Racket is in fact a "language-oriented" language. YMMV.

2 Likes

A few things I still miss from Classic Visual Basic 6:

  • Making a simple form with a few buttons and textboxs that everyone can use is very simple, extremely simple. (It would be nice to have a visual editor to build on top of racket/gui)

  • Ctrl+J programming. You write an object, press the period . or Ctrl+J and you get a menu with all the methods/properties of the object. That saves a lot of time looking at the docs if the method is call length or size, (probably impossible to solve, but perhaps in rhombus...)

  • Stop, edit and continue. Just put a breakpoint, wait, edit the code and press continue. It saves a lot of time of debugging and in exploratory programs. (This is almost incompatible with macros and any optimization of the code.)

  • I don't miss the lack of a sort function. I refuse to implement anything more complicated than buble sort, so I want a nice fast sort function in the standard library. (Probably the VB6 standard library has many more holes, but this is one that bit me.)

  • vectors that don't start at 0: I like 0 indexed vectors, but the alternative is useful to port programs from other languages or load/rewrite/save data designed for other languages. (is it possible to add compatibility/vectors1 ?)

1 Like

A quick note on (1): while reading this comment, I came across MrEd Designer. Very cool, and it reminds me of my similarly nostalgic experiences with NetBeans.

  • vectors that don't start at 0:
    I like 0 indexed vectors, but the alternative is useful to port programs from other languages or load/rewrite/save data designed for other languages. (is it possible to add compatibility/vectors1 ?)

I usually just allocate a vector one slot larger than needed and put #f in the the first slot.
For simple contexts this is usually enough, but one must pay attention when subvector and vector-length are used.

For larger projects it makes sense to have a designated vectors1 library,
but I don't think it's worth the effort of maintaining both as part of the language.

I do wish however, that Racket had a concept of "subvector" or "slice" that didn't involve copying.
A subvector of a larger vector, v, could be represented as a struct (sub v start-index end-index).

1 Like

Various array SRFIs (like my SRFI 231) allow vector (and array) indices to start at 1 (or any other number). They also have the concept of "slice" or "view" or ...

5 Likes

I think the slices can almost be implemented with impersonators, but the vector-length reports the true value.

1 Like