Design patterns in Go

8,661 views
Skip to first unread message

xavm

unread,
Oct 25, 2011, 3:37:23 AM10/25/11
to golang-nuts
Hello,
a non technical subject about Go :)
It could be interesting to see how the 23 band of 4's Design Patterns
would be implemented in Go, and to gather the answers into a
document...
regards
Xavier

Volker Dobler

unread,
Oct 25, 2011, 4:01:15 AM10/25/11
to golang-nuts


On Oct 25, 9:37 am, xavm <xavier.meh...@gmail.com> wrote:
> It could be interesting to see how the 23 band of 4's  Design Patterns
> would be implemented in Go,

Uh! The "Design Patterns" are patterns to solve problems which
are problems only because of the limited view of Java (and other
languages) on OO programming. (Slightly exaggerating :-)

A (pure) Java style OO pattern in Go is neither idiomatic nor
instructive:
To know how to perform one of the "23 tricks with a hammer" with
your tool set is not that useful if your toolbox contains
a screwdriver, a knife and a gripper but no hammer...

The GoFs patterns are useful, good and necessary and do help
communicating your ideas, but I'm always astonished how these
patterns are considered latest, absolute and only wisdom
in cs. I'm waiting for the "Design Patterns done in elisp"...

Regards Volker

egon

unread,
Oct 25, 2011, 4:40:51 AM10/25/11
to golang-nuts
> It could be interesting to see how the 23 band of 4's  Design Patterns
> would be implemented in Go,

As Volker pointed out, these patterns aren't the ultimate goal...

But it's still a good thinking exercise. Rather than trying to
implement
those patterns in go we should be rather thinking how to solve the
same
problems in Go.

Anyway here's a quick implementation of some creational patterns

https://gist.github.com/1311842

(I didn't compile the code actually so, there are probably mistakes in
it)

I didn't implement Builder, Factory Method as it's in structure
similar to Abstract Factory.
Singleton - not worth implementing, use a global variable if you need
to instead... both are usually ways of around design errors

tux21b

unread,
Oct 25, 2011, 5:07:21 AM10/25/11
to golan...@googlegroups.com
There is a great talk by Rob Pike called "Public Static Void" available
on Youtube. You might find it interesting:

He also talks about Design Patterns and one example there is the
pattern of a "function invocation" in Assembler. Now, nobody
needs this pattern anymore, because the language does it for you.
(Similar can be said about Iterators and range for example.) Rob also
cites Norvig:

"patterns are a demonstration of weakness in a language"

So, I can highly recommend the yt video as an introduction to those
subjects and to understand the motivation behind Go.

-christoph

xavm

unread,
Oct 25, 2011, 5:23:43 AM10/25/11
to golang-nuts
Design patterns comes originally from Smalltalk not from java ;)

xavm

unread,
Oct 25, 2011, 5:30:41 AM10/25/11
to golang-nuts
Thanks for the answers ..
I'm not agreed with the sentence "patterns are a demonstration of
weakness in a language" ...
The goal of this thread is also to give a summary of what we can do or
not ; studying design patterns are from "conceptual" point of view ;
implementing them in a language enables to see the power or not of a
language... It is a good information if such a pattern or another one
is directly implemented in Go. It only proves the powerfulness of the
language, not the obsolescence of the pattern. By giving
implementations examples we only show that Go is what we need to
design correctly big applications.
regards
Xavier

xavm

unread,
Oct 25, 2011, 5:40:40 AM10/25/11
to golang-nuts
Thanks Volker for your thoughts... Design patterns (but also Test
patterns, Architectural patterns, Enterprise JavBeans patterns, and so
on...) have been designed roughly twenty years ago.. As everything
changes, we could actually sort, filter or update them to make them
more useful for the current concerns. But the concept of "pattern"is
still useful as design means ; so why not thinking about useful
patterns (old or new ones) for Go...
regards
Xavier

On Oct 25, 10:01 am, Volker Dobler <dr.volker.dob...@gmail.com> wrote:

vruz

unread,
Oct 25, 2011, 6:55:53 AM10/25/11
to golan...@googlegroups.com
On 25 October 2011 11:07, tux21b <tux...@gmail.com> wrote:
> There is a great talk by Rob Pike called "Public Static Void" available
> on Youtube. You might find it interesting:
> http://www.youtube.com/watch?v=5kj5ApnhPAE

Great talk! Thanks for sharing.


>
> He also talks about Design Patterns and one example there is the
> pattern of a "function invocation" in Assembler. Now, nobody
> needs this pattern anymore, because the language does it for you.

Similar case, the Gtk GUI library, it's written in C in a way that
aims to be object oriented, but it's like playing a violin tuned two
octaves too high.

--
---- vruz
---- alterius non sit qui suus esse potest

Volker Dobler

unread,
Oct 25, 2011, 7:01:14 AM10/25/11
to golang-nuts

I'd like to object:

On Oct 25, 11:40 am, xavm <xavier.meh...@gmail.com> wrote:
> The goal of this thread is also to give a summary of what we can do or
> not ;

Can/cannot is a question about computability, Turing completeness,
(primitive) recursive (enumerable) functions and that like.
I think Go is pretty much universal regarding this can/cannot
issue.

> studying design patterns are from "conceptual" point of view ;
> implementing them in a language enables to see the power or not of a
> language...

I agree on this: It's never wrong to study things.
But on the practical side of getting stuff done (correctly, fast,
reliable) it's of minor concern.

> It is a good information if such a pattern or another one
> is directly implemented in Go. It only proves the powerfulness of the
> language, not the obsolescence of the pattern. By giving
> implementations examples we only show that Go is what we need to
> design correctly big applications.

I disagree completely: Being able to implement n out of m patterns
is _no_ sign of being capable die design big apps.

> Design patterns (but also Test
> patterns, Architectural patterns, Enterprise JavBeans patterns, and so
> on...) have been designed roughly twenty years ago.. As everything
> changes, we could actually sort, filter or update them to make them
> more useful for the current concerns. But the concept of "pattern"is
> still useful as design means ; so why not thinking about useful
> patterns (old or new ones) for Go...

I agree: That's Effective Go.

I think one should analyze the problem first, then choose the right
tool(s) and use them properly: The right answer to your problem might
be 40 lines of idiomatic shell script, 12'000 lines of idiomatic
Java or n lines of idiomatic python combined with m lines of idiomatic
fortran. If helpful: Use any pattern you like. But The focus should
be put on idiomatic, not on pattern.

Regards,

Volker

xavm

unread,
Oct 25, 2011, 8:14:11 AM10/25/11
to golang-nuts
Design patterns may also be considered as anti-patterns if you want ;)
We can do prose without knowing it, but it is even better to know that
we do prose, and how... Having a meta-view over things is always
useful, especially when we go from an old world to another one.
References change, concepts not. Knowing that a old knowledge is
obsolete or not is a a knowledge which is valuable. How many people
still analyze their pbs with SART, SADT, schlear et mellor, and so
on... ? not a lot... nevertheless, knowing concepts behind these
methods are still useful because they are finally the same, and
enables to know the essence itself of these concepts...
I developped in Smalltalk, in Java, in Lisp, CSP and many more
languages, but finally I'm language agnostics... Go is a nice language
I'm fond of to use... but it is only another language gathering the
same concepts we found in the language I mentionned... but maybe in a
nicer way... What is interesting in design patterns is the concept
itself of pattern which is far more than snippets or idioms... A
pattern describes a problem, a way of process it, when, in which
context, and so on... Knowing this is valuable from my point of view.
And even if I don't use the all 23 patterns (or other we could create
or identify), some are useful every days like the command pattern or
state pattern, even if you implment them diffrently the way they was
implemented 20 years ago...

best regards
Xavier

Rob 'Commander' Pike

unread,
Oct 25, 2011, 10:12:38 AM10/25/11
to xavm, golang-nuts
As has been said, that book is about solving certain classic problems
in Java, a language with a particular, restrictive programming model
and type system. Go isn't much like Java.

A concrete example: The Visitor Pattern.

This is a clever, subtle pattern that uses subtype inheritance to
implement a type switch.

Go has type switches, and therefore no need for the Visitor Pattern.

I leave the Singleton Pattern as an exercise.

So you're right, it is educational to try to implement those problems
in Go, but for the most part those *patterns* don't really apply. Java
code doesn't work well in Go, nor Go in Java.

-rob

roger peppe

unread,
Oct 25, 2011, 10:23:42 AM10/25/11
to Rob 'Commander' Pike, xavm, golang-nuts
i have been thinking about a web site that would consist
of a bunch of code walks on code in the standard Go
tree, each demonstrating some design pattern "in the wild".

rather than naming the patterns and/or drawing complicated
diagrams, each code walk would simply show aspects of how
real Go code accomplishes things, with a focus on
picking out common aspects that are generally useful.

i think people might find this useful, but YMMV.

Xavier M.

unread,
Oct 25, 2011, 10:39:52 AM10/25/11
to roger peppe, Rob 'Commander' Pike, golang-nuts
Hi Roger,
I personnaly find the idea valuable... Integrating design concerns into development is mandatory, and having at disposal for everyone a bunch of "Go patterns" which may be a common basis to process some kind of problematics is for me a good idea... especially when we have to share discussions with others... It is so simple to say :"I've used the XXX pattern to solve this problem, combined with the YYY one" rather than to digg into the code to know how it was done, especially when less and less people want to use some design toolbox like UML to describe a problem and the solution... At least, it may be used easily...
regards
Xavier

2011/10/25 roger peppe <rogp...@gmail.com>

The Beast

unread,
Oct 25, 2011, 5:13:42 PM10/25/11
to golang-nuts


On Oct 25, 1:01 am, Volker Dobler <dr.volker.dob...@gmail.com> wrote:
> [...]
> I'm waiting for the "Design Patterns done in elisp"...
>
> Regards Volker

http://norvig.com/design-patterns/ppframe.htm

(Slide 10 in particular is relevant)

-- Markus

Volker Dobler

unread,
Oct 25, 2011, 6:23:38 PM10/25/11
to golang-nuts
On Oct 25, 11:13 pm, The Beast <markus.zi...@gmail.com> wrote:
>
> http://norvig.com/design-patterns/ppframe.htm
> (Slide 10 in particular is relevant)
>

Thanks! It's exactly my point. 70% of the pattern just
"vanish" if the right tools are used: There is no
sensible room for "Fancy Hammer Trick" in the presence
of a screwdriver (if your problem is a screw...).

Volker

francoi...@gmail.com

unread,
Mar 14, 2014, 7:35:46 AM3/14/14
to golan...@googlegroups.com, xavm
Go's Type Switch is definitely not a replacement of the Visitor Pattern. The main reason for the visitor pattern is to break at compile time.

The Type Switch will only break at runtime.

-Francois

Rob Pike

unread,
Mar 14, 2014, 4:39:44 PM3/14/14
to francoi...@gmail.com, golan...@googlegroups.com, xavm
The main reason for the visitor pattern is to visit things; how it
breaks is a separate point.

-rob

RickyS

unread,
Mar 15, 2014, 4:17:24 PM3/15/14
to golan...@googlegroups.com, xavier...@gmail.com
Here's a good Go pattern:  Go concurrency patterns. I'm in the middle of reading it.

Oliver Plohmann

unread,
Mar 17, 2014, 6:36:01 AM3/17/14
to golan...@googlegroups.com, xavier...@gmail.com

This has already been done for a certain number of design patterns: Evaluating the GO Programming Language with Design Patterns.


A concrete example: The Visitor Pattern.

This is a clever, subtle pattern that uses subtype inheritance to
implement a type switch.

Go has type switches, and therefore no need for the Visitor Pattern.

The idea of using method overriding is that for new functionality you only need to create a new subclass and re-implement the method(s) to be overwritten and you are done. You don't have to know about any type switches in your or someone's else code (which you might not know too well) that you would have to extend.

I wrote a little article explaining some approach to mimic method overriding in Go: Inner Pattern to mimic Method Overloading in Go. This approach is not perfect, but I would prefer it over a case switch.

Cheers, Oliver



 

Rob Pike

unread,
Mar 17, 2014, 7:59:28 AM3/17/14
to Oliver Plohmann, golan...@googlegroups.com, xavier...@gmail.com
The Visitor Pattern, like many patterns in the "Gang of Four" (I was
never sure whether they appreciated the deeper ironies of that
sobriquet), shows not the strength of object-oriented design but
rather the weakness: such are the lengths one must stretch to achieve
simple goals. To paraphrase Dr. Johnson: The Visitor Pattern is like a
dog's walking on his hinder legs. It's not done well; but you are
surprised to find it done at all.

-rob

Oliver Plohmann

unread,
Mar 18, 2014, 10:07:02 AM3/18/14
to golan...@googlegroups.com, Oliver Plohmann, xavier...@gmail.com
I had a little bug in the sample in my blog with a missing Act() method in the Animal interface. I only pops up when you have an additional Mamal "subtype" other than Dog. The sample now also has some Cat type. This way it should also be easier to read now.

Think this solution has something to it as it does not cause some extra cost as with late binding. The only additional price is the actInner method, but I think it can be justified as you get a solution that does not break encapsulation.

-- Oliver

Robert Johnstone

unread,
Mar 18, 2014, 9:33:16 PM3/18/14
to golan...@googlegroups.com, Oliver Plohmann, xavier...@gmail.com
This comment is a little ironic, given that there was a blog post on golang.org recently describing design patterns for concurrency in Go.  Whatever the deficiencies of C++, I'm not certain that the existence of design patterns prove anything.

Sugu Sougoumarane

unread,
Mar 19, 2014, 12:03:00 AM3/19/14
to golan...@googlegroups.com, Oliver Plohmann, xavier...@gmail.com
Every language has its weaknesses. Why would Go be an exception?
The question is: How do the other language fare when you try to do the same thing?

Hai Thanh Nguyen

unread,
Mar 19, 2014, 7:10:52 AM3/19/14
to golan...@googlegroups.com, xavier...@gmail.com
I have an idea, we could try to implement the solutions for the problems in the GoF book in Go, the best way we could think of, that means we just try to find the best way/ways to do those things, be simple, efficient and elegant, very likely with a different pattern, NOT just try to reimplement the patterns because it wouldn't work.
It would be a github project, and may become a book, some more problems that are not in GoF book might added, it could even be the bible for Go code designing, it would help people learn to structure code the best way, the best Go way.

Péter Szilágyi

unread,
Mar 19, 2014, 7:41:09 AM3/19/14
to Hai Thanh Nguyen, golang-nuts, xavier...@gmail.com
Hi,

  IMHO, the problems in GoF arise *because* of the OOP model in targets. There's little point of solving those particular problems, when they don't arise in the first place. Solve the problems that exist, don't generate ones that don't. Go's programming model albeit similar, has many radical divergences over classical OOP, which makes most existing patterns void.

  For example, Sameer had a very nice presentation a while back about concurrency patterns in Go [1]. I would say that that is the correct way of approaching the "design pattern problem". I.e. write large scale, real world programs, and you will see the common things cropping up, which could then be extracted into a pattern. Not the other way around. Patterns emerge organically, but that requires time and code base.

  Furthermore, design patterns tend to have a very bad side effect on logical thinking. I.e. When you formalize a collection of patterns, people tend to believe that the those are the one true silver bullet savior ways of solving something. The inevitable side effect is, that people will no longer try and figure out the best solution to a given specific problem, but rather skim through the pattern collection and see which can be forced upon the problem best.

  Don't get me wrong, patterns are nice up to the point of general knowledge (i.e. if you have something similar to this, you *could* solve it somehow *similar* to that). Patterns are good to learn techniques, but imho they are the devil when taken literally.

Cheers,
  Peter

Refs:


--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Dan Kortschak

unread,
Mar 19, 2014, 7:48:57 AM3/19/14
to Péter Szilágyi, Hai Thanh Nguyen, golang-nuts, xavier...@gmail.com
This sentiment is one of the reasons I enjoy using Go so much. It tends
to promote the expression of algorithmic ideas without resort to cliche
(potentially synonymous for pattern).

Benjamin Measures

unread,
Mar 19, 2014, 8:12:07 AM3/19/14
to golan...@googlegroups.com, Oliver Plohmann, xavier...@gmail.com
On Wednesday, 19 March 2014 01:33:16 UTC, Robert Johnstone wrote:
On Monday, 17 March 2014 07:59:28 UTC-4, Rob 'Commander' Pike wrote:
The Visitor Pattern, like many patterns in the "Gang of Four"[...]:
such are the lengths one must stretch to achieve simple goals.
 
This comment is a little ironic, given that there was a blog post on golang.org recently describing design patterns for concurrency in Go.  Whatever the deficiencies of C++, I'm not certain that the existence of design patterns prove anything.

It is not the mere existence of these patterns but "the lengths one must stretch to achieve simple goals." It is the gymnastics one must perform [to work against language restrictions] to solve a simple problem. Popular patterns tend to typify the worst of these: for a pattern to become popular the problem must be trivial. The singleton pattern is a prime example, since the problem can be sumarised in 5 words: restrict instantiations to one object.

By contrast, the majority of the content of the blog post aluded to <http://blog.golang.org/pipelines> deals with pipeline cancellation for an "unknown or unbounded" number of processes -- subject matter which is non-trivial in any language.

Robert Johnstone

unread,
Mar 19, 2014, 11:18:24 AM3/19/14
to golan...@googlegroups.com, Oliver Plohmann, xavier...@gmail.com
Different languages target different levels of abstraction.  Following the idea below, the existence are design patterns in assembly to handle function calls means that no one should need to program in assembly any more.

Péter Szilágyi

unread,
Mar 19, 2014, 11:25:56 AM3/19/14
to Robert Johnstone, golang-nuts, Oliver Plohmann, xavier...@gmail.com
Hi,

  Take care not to mix up design patterns and levels of abstractions. Although we could argue that building function calls on top of assembly is a "pattern", it is one that raises the level of abstraction. The design patterns of GoF on the other hand do not provide higher abstractions, only control flow limits within the existing abstraction layer.

Cheers,
  Peter


--

Robert Johnstone

unread,
Mar 19, 2014, 1:16:43 PM3/19/14
to golan...@googlegroups.com
I think that you misunderstood my point.  My point was that since languages differ in their level of abstraction, the level of abstraction for the design patters will also vary.  Judging the quality of a language based on the level of abstraction of its design patterns is just as odd an idea as judging the language based its level of abstraction directly. 

Beyond the above, it's not clear why patterns should be said to raise the level of abstraction in one case and lower it in another.

DV

unread,
Mar 19, 2014, 2:15:02 PM3/19/14
to golan...@googlegroups.com
My interpretation of what was said above was more along the lines that some of the patterns in the gang-of-four book exist not because they're good patterns in themselves, but that they exist because the languages they were designed for have various shortcomings and a certain type rigidness that doesn't exist in Go, so why bother using them? 

Some sort of AbstractFactoryOfFactoryFactories is always present in every non-trivial Java project I've ever seen, but almost nobody bothers with it in Go. If that pattern is difficult to implement in Go (it might be, I never tried) what does that tell us about Go? That Go is bad at implementing bad/unnecessary patterns? I can live with that, definitely. The more important question though is - why even bother with that "pattern" in Go? 

I think we need to look at the problems, and try to solve them in Go, not look at a problem, take an existing Java solution and then translate it to Go. 

19/20 "patterns" I've seen about Go are about concurrency and how to use goroutines, channels, select, etc. to solve common concurrency problems, in Go. They're not abstract UML diagrams about problems that may not even exist in Go or other languages, which is what the GoF book is to me - answers to questions that nobody is asking. 

Ionenet SA

unread,
Apr 1, 2024, 12:20:17 PM4/1/24
to golang-nuts
I think many of you are confusing things. Many GOF patterns are still the basis of today's programming. For example, the way that React or Vue manage states, whatever you are using Pinia or Redux, they are no more than the Observer pattern combined with the Proxy. And they are now native in vanilla JavaScript. The observer is at the basis of event driven programming. The Model-View-Controller itself is another combination of GOF patterns. All the lambda functionality is an application of the Strategy pattern and there are plenty of examples in modern programming that they are nothing more than patterns. All the Martin Fowler's patterns are nothing more than a combination of GOF patterns. The entire functionality of history and ctrl+z/ctrl+y functionality is nothing more than a combination of State/Memento. So I disagree completely about the idea that patterns are to overcome Java limitations. The fact that some modern languages natively implement a pattern in the form of a construct (for example lambda functions to implement strategy) does not make the patterns useless, but rather illustrate their usefulness.

So, while some patterns are useless today, while some others are natively implemented in many languages, including PHP, knowing them is still very useful to understand how things work and where they come from. Otherwise you will get submerged by a myriad of fancy names (in Laravel's style) and you have to figure out and finally learn the same wheel with a different name and the incorrect way.

Think about it.

Cleberson Pedreira Pauluci

unread,
Apr 1, 2024, 9:44:57 PM4/1/24
to golang-nuts
This site shows how to implement some design patterns in Go and other languages through examples. https://refactoring.guru/design-patterns/go

Cleberson Pauluci.

alex-coder

unread,
Apr 4, 2024, 6:00:38 AM4/4/24
to golang-nuts
Hi All,

in case someone is in interest of the subject I repost here what I have found in the internet some time ago.
>>I apologize for being so intrusive.
>>I will only provide links to educational resources, in case it would be interesting for anyone.

But I would like to stress one thing.
Due to absence in GO dynamic dispatching some of the patterns must be implemented, say as they must be in GO. :-)

Thank you.

понедельник, 1 апреля 2024 г. в 19:20:17 UTC+3, Ionenet SA:
Reply all
Reply to author
Forward
0 new messages