| Though I agree about the point about not creating objects/instances where a pure function will get the job done, I disagree with the general stance against OOP. I think OOP is absolutely essential to simplicity. FP tends to lead to too many indirections with data traversing too many conceptual boundaries. FP (if used dogmatically) tends to encourage low cohesion. I want high cohesion and loose coupling. Some degree of co-location of state and logic is important since that affects cohesion and coupling of my modules. The key to good OOP is to aim to only pass simple primitives or simple cloned objects as arguments to methods/functions. 'Spooky action at a distance' is really the only major issue with 'OOP' and it can be easily solved by simple pass-by-value function signatures. So really, it's not a fundamental issue with OOP itself. OOP doesn't demand pass by reference. Alan Kay emphasized messaging; which is more leaning on 'pass by value'; a message is information, not an object. We shouldn't throw out the baby with the bathwater. When I catch a taxi, do I have to provide the taxi driver with a jerrycan full of petrol and a steering wheel? No. I just give the taxi driver the message of where I want to go. The taxi driver is responsible for the state of his car. I give him a message, not objects. If I have to give a taxi driver a jerrycan full of petrol, that's the definition of a leaky abstraction... Possibly literally in this case. That said, I generally agree with this article. That's why I tend to write everything in 1 file at the beginning and wait for the file size to become a problem before breaking things up. There are many different ways to slice things up and if you don't have a complete understanding of your business domain and possible future requirement changes, there is no way you will come up with the best abstractions and it's going to cost you dearly in the medium and long term. A lot of developers throw their arms up and say stuff like "We cannot anticipate future requirement changes"... Well of course, not on day 1 of your new system!!! You shouldn't be creating complex abstractions from the beginning when you haven't fully absorbed the problem domain. You're locking yourself into anti-patterns and lots of busy-work by forcing yourself to constantly re-imagine your flawed original vision. It's easier to come up with a good vision for the future if you do it from scratch without conceptual baggage. Otherwise, you're just seeding bias into the project. Once you have absorbed it, you will see, you CAN predict many possible requirement changes. It will impact your architecture positively. Coming up with good abstractions is really difficult. It's not about intelligence because even top engineers working in big tech struggle with it. Most of the working code we see is spaghetti. |
Indeed if you pass by value/use immutability where feasible, you already avoid most of the issues I’m warning against, so it sounds like you found a sensible way to apply it while avoiding the pitfalls.
> If I have to give a taxi driver a jerrycan full of petrol, that's the definition of a leaky abstraction... Possibly literally in this case.
:D