2

My first introduction to programming was Java, which was horrible so I learnt Actionscript3 which was nice... "The point is" OOP was my introduction to programming where by I went on to gain a career in PHP and while I can confidently write programs/scripts in imperative languages I am no where near as comfortable in doing so.

The primary reason is because I am unable to understand how imperative/procedural languages can be extended in the same way OOP languages use polymorphism and substitution.

I am now looking to learn additional languages and may even have a crack at C, only if I can work out the basic principles for substituting functionality.

Can anyone explain the basic principles used to extend the functionality of a library/function without re-writing that entire function. Because in OOP you would override one method of a class and possibly call the super method to retain some of the original behavior.

  • 1
    @gnat I read over those, and they are interesting. But I am trying to find out what the equivalent for inheritance is in non-OOP languages. Those links don't really explain that. – Flosculus Oct 31 '14 at 16:25
  • 1
    not bad, edited question doesn't look like a duplicate anymore. By the way, since you mentioned C, are you aware of function pointers and how these work? – gnat Oct 31 '14 at 16:45
  • 1
    There's some minor conceptual problems here, because you most mainstream OOP programming languages (including Java) conflate abstract data types with objects and because inheritance is not an essential feature of OOP. Despite common parlance, Java classes are not objects, they're abstract data types. C can do abstract data types easily enough with opaque structs. Instances of Java interfaces are objects (in the OOP sense), and there's no safe way of implementing them in C, because C doesn't have closures. So you can make a struct of function pointers, but you have nowhere to put... – Doval Oct 31 '14 at 17:04
  • 1
    ...instance variables, unless you add a single void pointer to the struct which points to where the instance data is, but then you have to cast to get the data and risk undefined behavior. – Doval Oct 31 '14 at 17:05
  • 1
    Actually, the modern Linux Device Driver Model, which was introduced about 10-15 years ago, I think, is maybe not purely object-oriented but heavily based on OO ideas. It's not coincidence that the central struct which holds it all together is called kobject. – Jörg W Mittag Oct 31 '14 at 17:26
6

If you want a good example of full-fledged OOP in C, take a look at GTK+. Mostly, your constructors have a lot of boilerplate to initialize things like vtables and keep track of a type hierarchy. Creating your own object for GTK+ is a good way to learn what most OO languages do for you behind the scenes.

One thing you'll learn by writing some real code is that virtual methods are not as common or necessary as you would think they'd be. Programmers have a tendency to overuse inheritance. Most of the time, you know exactly which static function you need to call, and you're just sharing a simple data structure between several different functions. You extend it simply by creating a new function that works on the same data structure. This is how the vast majority of procedural code works.

When you do truly need virtual methods, you just add function pointers to that data structure you pass around. Then perhaps create a wrapper function to encapsulate the ugly function pointer syntax. See here for an example of how that's done in GObject, the object library of GTK.

If you need to potentially add fields, that data structure you pass around typically has a void* or something where you can store implementation-specific data.

Again, write a real app in GTK+ as a learning exercise, and I think you'll find the patterns somewhat familiar, once you get past the syntax.

  • "You extend it simply by creating a new function that works on the same data structure." I figure that underneath, that is what always happens regardless of paradigm. Thanks, this makes it clearer to me. – Flosculus Nov 3 '14 at 10:26
1

I think the easiest way to understand this is by looking at a simple example in C: the qsort function of the standard C library. As a user of that lib, you can provide an arbitrary comparison function to qsort here without touching or recompiling the library.

Another good example was shown in this former SO post. It exaplains how to build the equivalent of a String class in C, and how to emulate inheritance.

0

This recent blog post by Bob Martin is relevant. In it, he defines providing convenient ways to implement polymorphism as being the essential element of what makes a language object-oriented.

In light of this, we can read your question as "how do I do object-oriented programing in a non object-oriented language?" The answer to this is quite simple: you don't if you can possibly help it. Yes, it is possible to implement it in many such languages, but the results are always unpleasant and difficult to read or work with. If your problem involves the need to handle different types of data in similar ways (i.e. if it is essentially a polymorphic problem) then use an object oriented language. If you have to work in a non-oo language, try to unify your data such that you never need to handle different types at the same place in your code. Learn to worry less about repeating yourself: it's much harder to avoid in non-oo code. And use function pointers as a last resort, when you absolutely need them only.

  • The more I read Uncle Bob's posts, the less I respect him. The guy has no idea whatsoever about what FP is. No shame in that; there's plenty I don't know either, but I least I try not to rant about it as if I did. Examples of things he gets wrong: he speaks of polymorphism as if naturally belonged to OOP or FP didn't use it (wrong), he ignores higher-order functions as the natural way to do what he calls "source inversion", "too many parenthesis" is not something found in FP (maybe he got confused with Lisp?), "true functional programming has no assignment" (oversimplification), etc. – Andres F. Nov 29 '14 at 16:17
  • It drives me mad that Uncle Bob feels confident enough to write about the differences/similarities between OOP and FP when he clearly is familiar with only one of the two! – Andres F. Nov 29 '14 at 16:21
  • 1
    I can't really comment on the FP aspects of the article, as my functional experience is rather limited, but from the limited perspective of defining what the critical core of OOP is, I think the article's spot on. – Jules Nov 29 '14 at 16:47
  • I just found the talk which has the slide Uncle Bob was ranting against. It's interesting. If I were a software engineering guru and published author like Uncle Bob, I would have taken the effort to find the talk and see what it has to say. Maybe, just maybe, he's just mistaken about FP because he's unfamiliar about it. But he gives no indication in his post he did so, which doesn't surprise me... – Andres F. Nov 30 '14 at 18:07

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.