6 ms·
Golang Object Oriented Design
- pjmlp 13y agoFor an understanding how to do OO design in Go, learning about component programming is a good way. http://www.amazon.de/Component-Software-Beyond-Object-Oriented-Programming/dp/0201745720 http://www.amazon.de/Component-Software-Beyond-Object-Orient... The first edition used Component Pascal from the Oberon family, which Go gets some influence from. Later editions used Java and C# instead. Additional learning about how COM and XPCOM work is also a way to get some ideas.
- discreteevent 13y agoYes Go is similar to COM in that it focuses on interfaces and leaves out implementation inheritance which causes so much trouble. COM was way ahead of its time on that. "Component Oriented Programming = Polymorphism + (Really) Late Binding + (Real, Enforced) Encapsulation + Interface Inheritance + Binary Reuse" Apart from "Binary Reuse", the definition above is what object oriented programming is really all about (I think).
- drunken_thor 13y agoHere is the article that got me onto the way of go: http://areyoufuckingcoding.me/2012/07/25/object-desoriented-language/ http://areyoufuckingcoding.me/2012/07/25/object-desoriented-... The memes are a bit much but the content is solid.
- Touche 13y agoIs there any advantage to using OO in a language that doesn't have classes or inheritance? Does declaring a method on a type give you something that declaring a function that takes the type as an argument doesn't?
- riobard 13y agoOO does not have to use classes and inheritance. OO is about encapsulation of data and behaviors. Declaring a function on a type lets you specify the behaviors of the type. In particular, in languages like Go with interfaces, it allows you to have a contract of behaviors independent of implementations. You cannot do that with plain functions.
- masklinn 13y ago> Is there any advantage to using OO in a language that doesn't have classes or inheritance? Like Self or javascript?
- adamlett 13y agoJavaScript and Self don't have classes, but they do have inheritance.
- masklinn 13y agoSelf has delegation. Conflating delegation and inheritance is no better than conflating embedding and inheritance.
- munificent 13y agoDelegation seems pretty similar to inheritance to me. What am I missing?
- masklinn 13y agoIt doesn't set up is-a relationships and can be used for significantly more than differential inheritance (IIRC Self uses it for scoping).
- laumars 13y agoThe lack of inheritance and creation methods are a bit annoying at times (particularly the latter), but there's still benefits of adopting an OOP approach in Go. For example, say you're writing a CMS and want to make strings like the article title to be used in the URL (for readable URLs and SEO), displayed in HTML (eg inside heading tags) and also potentially used for string comparisons, you'd need to have a function to URL / HTML encode the string and you'd need to remember to do it each time you outputted the string. This can make it very easy to introduce vulnerabilities where you forget to HTML encode the string. With methods, you can force the developer to state which format to output the string as: type DisplayText struct { Value string } func (dt DisplayText) HTMLEscaped() string { return html.EscapeString(dt.Value) } func (dt DisplayText) URLEscaped() string { return url.QueryEscape(dt.Value) } var article_title DisplayText So now when ever you call article_title, you have to specify the string encoding. Which is not only more secure (eliminates the risk of forgetting to encode your string), but also more readable: fmt.Println(article_title.HTMLEscaped) vs fmt.Println(html.EscapeString(article_title))
- qznc 13y agoOOP is about polymorphism. Classes and inheritance are not necessary, just like encapsulation or private data. In long: http://beza1e1.tuxen.de/articles/oop.html http://beza1e1.tuxen.de/articles/oop.html The question is not where the type syntactically is. The question is, if the dispatching between functions/methods happens dynamically or statically.
- pjmlp 13y agoThere are many ways to implement OO. Self, JavaScript, CLOS, Go, BETA, Clojure Protocols, Type Classes, COM and probably quite a few others. What most mainstream developers know, is not the only way.
- patrickg 13y ago+1 for mentioning BETA. Any actual user of that language?
- pjmlp 13y agoI got to learn about it when I attended ECOOP'99. Never saw it outside the conference.
- patrickg 13y agoBETA was the beginner's language at the University of Dortmund (Germany) back in 1996/7/8. Never saw it outside of these buildings.
- draegtun 13y agoBETA did come up in this HN post from last year: The impoliteness of overriding methods - https://news.ycombinator.com/item?id=4943538 https://news.ycombinator.com/item?id=4943538
- 13y ago
- luikore 13y agoToo many people were trained to think in the OO style, especially class-based OO, no matter if it fits the problem or not. Any language with prototype but not classes will end up with hand-crafted classes. Any language without neither will end up with hand-crafted prototypes.
- ori_b 13y agoYes. It gives you Liskov substitution.
- dragonwriter 13y ago> Is there any advantage to using OO in a language that doesn't have classes or inheritance? Yes. Really, interfaces are all you need for OO; class are just types-that-also-define-interfaces, and inheritance is just a shortcut for interface implementation. While I think Go's implicit interface implementation is pretty much 180-degrees off the best way to do OO w/o classes and inheritance (I'd prefer explicit interface implementation, which eliminates interface collision), I do think clasess and inheritance get in the way more than they help.
- fauigerzigerk 13y agoI keep wondering if Go couldn't have gone further in getting rid of the cruft that has accumulated around OO. Go doesn't have an implicit "this" pointer. It doesn't have members that are private to an individual object nor members private to a type. Encapsulation exists only at the package level. Yet Go keeps that old OO concept of method receivers. Why? I never found it very plausible to have one special case parameter with its very own syntax, but with type level encapsulation it did at least have some justification. Without this kind of encapsulation, the only remaining purpose of the receiver is method dispatch. But why dispatch based on the type of one parameter and not the others? Multimethods would have been the logical conclusion of the OO cleanup that Go's designers apparently intended to achieve.
- dualogy 13y agoWithout method receivers you wouldn't have methods, only funcs. Then you'd end up calling your "methods" names like `Address_Compare(addr1, addr2 Address)`, `Address_ToString(addr Address)` and so forth. How unpleasant that'd be! With method receivers, you can have `addr1.CompareTo(addr2)` and `addr.ToString()` etc..
- exDM69 13y ago> Without method receivers you wouldn't have methods, only funcs. Then you'd end up calling your "methods" names like `Address_Compare(addr1, addr2 Address)`, `Address_ToString(addr Address)` and so forth. Methods are just a limited special case of functions. Also, there are various different semantics that are used in function application. Your view of function application is rather limited, you might want to study e.g. how functions are applied in Haskell (type classes) or Common Lisp Object System (CLOS, multimethods). Both of them use very different semantics to what you're used to. In addition, good namespacing and module systems can solve a big part of the "problem" you mention. Most modern languages have more than one giant global namespace.
- mercurial 13y ago> Methods are just a limited special case of functions. Also, there are various different semantics that are used in function application. Your view of function application is rather limited, you might want to study e.g. how functions are applied in Haskell (type classes) Well, sure. On the other hand, if you had receivers for record accessors, you wouldn't end up with the ugly prefixing necessary in Haskell.
- mostafah 13y agoOne of the most common problems people have when they get to know Go is to not embrace its approach to programming, but try to enforce what they already know in Go programs. This is a clear example of that. Implementing “polymorphism” with Go interfaces is abusing interfaces! Seeing embedding as inheritance misses the point of both embedding and inheritance. Comparing packages to namespaces isn’t that bad, but just delays you getting to know Go for real. I’m not saying that these old concepts are bad or Go’s new approach is superior. (I believe in that; but that’s not the point here.) I’m saying if you’ve gotten used to these concepts so much that you can’t think or program without them, then there’s a problem. Don’t design a solution around polymorphism or inheritance and then try hard to force that into Go. Design your program with that your language is giving you.
- davedx 13y agoI see pretty much the same problem with JavaScript. It's everywhere -- framework developers are busily implementing polymorphism, inheritence etc. all over the place. Yet I can't recall ever choosing to use "inheritance" instead of composition in my JavaScript projects.
- burntsushi 13y agoDid you RTFA? The conclusion has: > Composition, embedding and interfaces provide powerful tools for Object-Oriented Design in Go. Thinking in terms of inheritance really doesn't work. Trust me, I tried. The OP is clearly trying to introduce ideas in Go by relating them to other ideas you might be more familiar with. This is, IMO, very much distinct from trying to shoehorn design techniques from other languages. In fact, the OP is rather explicitly agreeing with your point and trying to remedy it. > Implementing “polymorphism” with Go interfaces is abusing interfaces! Go's interfaces use structural subtyping, which is a form of polymorphism.
- herge 13y agoI have a question about go. Let's say I have a struct Foo and a function/method for Less. What is the quickest way to sort an array of Foo's? Do I have to implement my own []Foo type with all three methods as described in the sort package?
- nickpresta 13y agohttp://golang.org/pkg/sort/#example_Interface http://golang.org/pkg/sort/#example_Interface
- herge 13y agoSo the answer is yes, I have to implement the whole interface?
- stonemetal 13y agoYes, to use code that relies on an interface you must implement the interface for your types. That is one of the reasons go has a guiding design principle that interfaces should be as small as possible.
- bouk 13y agoYes, generics are not (yet??) possible in go
- munificent 13y ago> To apply the uniform access principle to the Part type, we could change the struct definition and provide setter/getter methods If you have to apply it, it isn't uniform access. The point of the principle is that the call-site shouldn't distinguish between getters and fields so that the implementer can change that decision freely without breaking callers. Nice article, though!
- nathany 13y agoThanks for the clarification.
- noelherrick 13y agoGood article - this covers the basic OO patterns in Go. I really like the simplicity of the design - objects are just structs and you can define a method for that object. Coming from C#, it's like every method is an extension method. The only critique I have is that there's no way to verify that object X implements methods A, B, and C. When I'm using C# or Java, I often use an interface as a test to make sure I've done my work since the code won't compile if a class that extends an interface fails to implement all the methods.
- gmi01 13y agoTo verify that Concrete implements Interface use this: var _ Interface = Concrete{}
- lnmx 13y agoThe compiler will complain if you attempt to assign (or assert) a value to an interface that it cannot fulfill. ex. http://play.golang.org/p/OLTHIXjgy8 http://play.golang.org/p/OLTHIXjgy8
- nathany 13y ago"Compared to duck typing, interfaces are statically checked and documented through their declaration..."
- crazygringo 13y agoOff-topic, but it would be nice if the blog didn't use 24-pixel body type, so that I could see more than a handful of lines at a time on my laptop. I've never seen a book with 24-point body type, except possibly for the visually impaired or 3-year-olds. Heck, most headings aren't even 24 point. What is it with this blog trend of gargantuan type, which seems increasingly common? It's totally out of proportion with the rest of anyone's OS and computer interface, and all the common sites. I'm really getting tired of having to zoom out to an insane 50% level just to make things legible again.
- nathany 13y agoOff-topic: You'll be disappointed to learn that I also use an 18-pt font in my editor. I happen to like big readable text, maybe something to do with my age and my prescription being -5.5. P.S. the font-size is actually 1.5rem
- throwit1979 13y ago34yo, -9.5 here, and I prefer 10pt fonts for code. Do you not wear your glasses and/or contacts when working? I don't follow.
- jasomill 13y agoThis preference could also depend on the font and what's rendering it; on my Thunderbolt Display, while "18pt" Consolas renders at less than 7 points wide using OS X defaults, Windows 8, using defaults for the same display, renders the same font at around 8.5 points wide by default, and Myriad Pro's "M" at nearly 13 points wide. Since 13/7 is approximately 18/10, your respective preferences may not be as different as you think.