Faithful OOP vs. Association
So per @AntonAntonov's suggestion I'm going to chime in on OOP vs. Association. In a comment, @Eric notes that:
"By the way, with the Association, namespace mechanism and the highy
flexible rule-replacing system(contain functional programming as its
small feature) in Mathematica, I roughly guess that there would be no
need to think with or implement OOP anymore."
While this is partially true, I think there are a few things to consider (and note that I'm not really a programmer, so I might be spouting garbage here):
- OOP is a paradigm, not a framework, so OOP can still be useful even if an OOP-framework is less useful that it would once have been
- OOP and
Association are fundamentally complementary
I think that last point bears some discussion, and to ground it, I'll disclose that I am biased, as most of my user-accessible code in Mathematica is object-oriented in some way. It might be code-as-data level psuedo-OOP, it might be true mutable OOP, but the paradigm is simply too useful to abandon altogether.
To start, let's consider struct-level OOP.
Association makes this super easy. Just do something like:
and you have a struct. I use this type of deal a bunch, for example here to represent notebook tabs in the
To make this more useful, maybe we'll take our OOP one step further and attach some head to it, to make it a code-as-data level object:
Then we can stick
Format code on
UpValues and junk like that. This is a powerful tool, and one of the most common ones I use.
This is most useful when you don't need to mutate your data. Generally you can get away without mutability, but sometimes it's just too useful to do without. And here's where you generally need some form of OOP framework. And here is also where we should take a detour to look at the (other) favorite language of jokes and hacks like me, python.
OOP association-wise in Python
Python is a fully-OOP language. With perhaps the exception of the most primitive of primitives, there is nothing but OOP in python. And what do python's objects look like in practice? Glorified hash-maps, which are implemented in Mathematica as associations. And if you pretty much just copy python's structure but copy it over to Mathematica, it's easy and powerful. And if you take some time to optimize, that's even better. To give a sense of just how easy, over about a year-and-a-half I've implemented 4 or so such frameworks.
The basic idea I've used is either that you make a wrapper head that holds a
Symbol that can be mutated or, as I've been doing recently, making a single centralized holding symbol that tracks object and type data in a core
Association and making a head that holds a pointer to an entry in that. I've found the latter to be somewhat more efficient and manageable. Note that we can do this in either a typed or untyped manner.
We need some mutability, but since we're working with a
Symbol in either case we can get that out of a combo of
SetDelayed. We can even vectorize the
AssociateTo for efficiency.
And this truly is useful. It's got overhead for sure, it's relatively slow, yes, but as with everything Mathematica, if you know how to use it right, it can take you far. I use one such framework in a large chemistry package of mine, I used another version in a now-abandoned set of classes for a specific type of QM computation with random additions for databases and parallel objects and junk, and I developed one just as an exercise which I'm gonna get around to putting through its paces at some point.
Just to comment on Anton Antonov's first question, I think if some OOP framework were integrated into the language it would be incredible, but I also totally understand why WRI doesn't put it in.
Additional comparison between Association and OOP over handling of "global" variables can be seen in this MSE answer of "Functions with changeable global variables".
I made another few implementations here and here for the question How can I implement object oriented programming in Mathematica?