Aug 2, 2022Liked by Laszlo Sragner

Szia Laszlo,

Hogy vagy? :) I take you up on your word at the end of this article. Would love to have the continuation of this article with how further design patterns are useful for data science.

Any chance on a follow-up article with Bridge Pattern - to join data with model, Adapter Pattern - to do dependency inversion, Builder Pattern - to build complex classes.

Koszonom, Timi

Expand full comment

Szia, Timi!

Koszonom, jol vagyok!

Since writing the article the only new pattern that we found conceptually relevant was the Adapter Patterm. If you would like to know how it incorporates into our programming driven ML paradigm please take a look at the slides at my talk: https://laszlo.substack.com/p/slides-for-my-talk-at-pydata-london (or watch the talk itself).

The Bridge Pattern is too similar to the Adapter Pattern so I'd rather not elaborate on it (I am also not sure I can communicate about them succintly).

The Builder Pattern is less relevant in Python because of the default arguments in the constructors. In special cases when the construction of an object is convoluted and one must ensure the object is always in a consistent state it can be relevant. I will write about it when I find the right example (relevant to ML).

Thanks for your comment!

Expand full comment
Nov 7, 2021Liked by Laszlo Sragner

Hi Laszlo, thanks for the write up – it's easy to understand, and yet very illustrative of the advantages of the programming patterns.

Since Python treats functions as first-class citizens, I wonder what you think about using functions instead of classes in some scenarios, like the StanfordNLPLemmatizer, which is a class with just one method besides the __init__, and while it have state (self.pipeline), it's instance is never used more than once.

Classes have (hidden) state, that can lead to subtle bugs, whereas (pure) functions do not, so while a class is more extensible as the need for complexity grows, for these "simple" examples, I think a function could do just as nicely... but I would love to hear your perspective on that!

Best regards, Allan

Expand full comment

This is a great point Allan, thanks for that.

First of all code quality is not attached to style, the same readability and decoupling principles can be achieved in all paradigms. It just happens that most of my experience in that field and I won't be able to write at this level about functional style. If you go to the https://mlops-community.slack.com/ #production-code channel there are usually lively discussions on this.

Second: The single method class is exactly the feature of the Strategy Pattern. Single-use is not necessarily a problem, this is a really simple exercise and usually this kind of decoupling helps if you have some complicated workflow. Like you want to be sure you are using the same lemmatiser in both training and evaluation. Decoupling can be justified for restructuring purposes only.

Third, and this is where my lack of functional experience stops me from drawing a conclusion because I don't know the equivalent in FP.

Instantiating the pipeline is a very costly operation that you only want to do once. It requires a lot of parameters to deal with subtleties (I only listed one but there are many). The pattern allows this to move out of the usage and keep these at one place so it doesn't pollute Process.run(). Until you have a handle to the lemmatizer you don't need to worry about it.

This is a very common pattern/anti-pattern in ML that you pollute your code with parameters of complex subsystems making the code fragile to change. This is the exact reason why I chose this pattern as one of the two mentioned.

In FP maybe currying helps you, but how many DSes know that or even want to use that? (I mean in anger in practice not just to the extent of school examples).

Thanks for the comment, I hope you have good success about thinking code.

Expand full comment

Hey Laszlo,

I might be a little late to the party on this one but great article series! I love how you are able to illustrate these concepts with concrete and simple examples.

I'd love to see examples of the three above-mentioned patterns being applied to better understand where they can come in handy!

Expand full comment