When reading your section on Python and ending statements with "pass", and after not finding other references to it in your blog, I have to ask about Ruby. It seems like it would check many boxes (highly extensible, no significant whitespace, begin-end blocks, quite lispy...). If you've played with Ruby, what drawbacks have you found?
What are the major advantages you found in Python and in what cases do they exceed those in CL (aside of e.g. the type system you wrote about in 2008)?
I've never written any Ruby code but I did look into it once. What turned me off was its extreme approach to object orientedness. If I want to add two numbers I want to be able to write (+ x y) or x+y. I don't want to have to write x.add(y). That's weird syntax in service of an ideology that I don't subscribe to.
There were a couple of other weird things that turned me off but I don't offhand remember what they were.
This doesn't mean I think Ruby is a bad language, just that it had some in-your-face features that didn't resonate with me.
Although the early versions weren't so, after the replacement of the base object model (see new style classes), in Python everything is an object as well, and many seem to miss that.
That's true, but actually using a literal as a object is forbidden by the syntax.
Python 3.8.9 (default, Mar 30 2022, 13:51:16)
[Clang 13.1.6 (clang-1316.0.21.2.3)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> 1.__abs__
File "<stdin>", line 1
1.__abs__
^
SyntaxError: invalid syntax
>>>
Yeah, I was misremembering the details. But here's an example of the sort of thing that I don't like.
If I want to convert a number to a string, I do:
x.to_s
which would lead me to think that to take the square root of a number I would do:
x.sqrt
but I don't. It's:
Math.sqrt(x)
So for every operation I have to remember whether it is invoked by x.op or op(x). In Lisp I don't have this cognitive load. It is always (op x).
That is not unique to Ruby. What is unique to Ruby is that the x.op style is applicable to literals. So you get weird things like 3.14159265.to_s which just looks bizarre to me.
What are the major advantages you found in Python and in what cases do they exceed those in CL (aside of e.g. the type system you wrote about in 2008)?