← Back to context

Comment by antonymoose

20 hours ago

Wildly controversial!

I look at OOP Patterns as standards and practices.

The same way we have building codes for staircases the framing of walls and electrical installations to prevent injury or collapse or fire.

Sure, you can dodge a lot of design pattern paradigms and still make a working application that makes money. You can also invent your own system when building your house and maybe nothing bad will happen. That tragedy hasn’t yet struck does not make the building codes bad just because you got away with it.

A decent chunk of OOP patterns was due to lack of language features, notably passing and returning functions

  • It's both.

    The *concept* of patterns makes sense. A shared language that developers can use when building things.

    The *reality* of patterns has been much less useful. The original ones were indeed a reaction to warts in the popular languages of their era. And as we tend to do in our industry, these have been cargo culted along the way and for some reason I still see people talking about them as first class citizens 30 years later.

    People don't seem to realize that patterns should be and are fluid, and as our industry evolves these patterns are evolving as well. A major difference between software engineering and the analogous fields people use when talking about patterns is those industries are much older and move less quickly

    • A pattern is exactly what the word "pattern" implies; something that lots of people seem to have found useful, so you might find it useful too.

      If you are a language designer and you see lots of people writing the same boilerplate, it behooves you to put it into the language. A pattern is a desire path - pave it. In that sense, they are missing language features.

  • Since a single-method object easily serves the role of such a function, that’s simply not true. Looking at the 23 GoF patterns, I can’t identify any that would be obviated by having first-class functions (or lambdas, as many OO languages nowadays have). Some of the patterns can employ first-class functions (e.g. an observer could be just a callback function reference), but the pattern as such remains.

  • The language feature isn't "passing and returning functions" but "loose coupling." Lambdas and Functors are just a way to represent that in OOP languages that care more about inheritance than about messaging.

  • A lot of patterns have become frameworks, or language features, yes. It's just paving cowpaths.

  • Are you referring to function pointers?

    I believe C has allowed passing and returning functions from... the jump, no?

    • I recall a lot of this comes from Java 5/6 where I think passing function pointers around was difficult, if not impossible. Back in those days, I had many a conversation with a friend who would ask "can Python do pattern/feature X?" to which I'd respond "it doesn't need to."

    • Not just function pointers. E.g. in Scala:

          def addX(x: Int): Function[Int,Int] = {
              y => x+y
          }
      

      addX(5) then returns a function that adds 5. So closures, which are equivalent to objects (behind the scenes, the compiler needs to allocate a structure to remember that 5 and know the "member function" to call to do the plus), and usually more straightforward.

      Once you get used to doing this, you realize it's useful everywhere.

      In a decent language with functional programming and generics support a lot of GoF patterns can be directly encoded as a simple type signature where you receive, return, or both some function, so there's not really much else to say about them. Like half of the behavioral patterns become variations of the interpreter pattern.

      2 replies →

    • You can return function pointers but not first class functions, which means you can’t do closures and other FP things in C

Design Patterns is more like the Human Factors and Ergonomics Handbook.

You can have your building engineered, in which case building walls out of 2x6's 16 inches on center is not off the table, but neither is a mortise and tenon timber frame with partition walls. In that paradigm, the code tries not to be descriptive of an exact technique but only gives you criteria to satisfy. For example you could run all of your electrical wiring on the outside of the walls or on the outside of the building, and you could use ramps instead of staircases. It only talks about ingress and egress for fire safety, and it explains how you're supposed to encase wires, or if wires are not encased it describes the way the wiring must be sheathed to protect the occupants.

You can heat your house entirely with an open fire, and the code speaks to how to do that safely. So it's unlike "design patterns" in a lot of ways in that the code tries to accommodate the kinds of buildings we try to build and the ways in which we modify buildings because that's easier than saying "these are all the allowed ways of building an entry staircase." Design Patterns are more in the latter category.

  • I disagree with that take. Design patterns are a language for (= give standard names to) patterns that tend to repeatedly occur in code, so that we can efficiently communicate about them. Programmers working in the respective contexts tend to reinvent them sooner or later if they don’t know them already, so it makes sense to circulate the knowledge about them. But that doesn’t mean that they are prescriptive.

    • You aren't wrong. The problem with this is the overuse of it. Its the main thing people criticize Java for. Even though it doesn't have anything to do with Java language but instead has to do with Java the business ecosystem or culture. When these are overused, that's when it becomes an in-group/out-group jargon thing.