Tuesday, September 17, 2013

Coding 101: Object Oriented Programming

Next topic, let's talk about 'Object Oriented Programming', often abbreviated OOP.  OOP is a topic that often comes up when talking about programming languages.  So what is it exactly?

OOP is the concept of treating the world as a collection of objects.  If you want an apple in your program, create an apple object, if you want a dog in your program, create a dog program.  Internally, these objects have properties which describe them, for apples you might have a property for color and another for shelf life.  For a dog, you might have properties like breed or age.

So far so simple right?  Every 'thing' that you want to exist in your program should be defined as some kind of object, easy.  Generally, when talking about OOP, these objects are represented as classes.

So, what does OOP accomplish for programmers?  OOP often times is described as allowing for a particular set of things.  Depending on who you talk to, you get different answers, as I was taught OOP allows for 3 things, encapsulation, inheritance, and polymorphism each of which I will talk in detail if you wish to continue.

Let's start with encapsulation as it is usually the first one taught, not necessarily the easiest, but the first one taught.  The idea behind encapsulation is to restrict access to properties or methods of an object.  In many languages that employ OOP as a paradigm include keywords like public or private which denote whether a property or method is publicly available to be called or not.  The reason why encapsulation can be related to the world can be shown in this manner.  Imagine private properties as inherent traits.  For a person you might imagine that their personality is an inherent trait in that you cannot really access a person's personality directly.  However, their actions (public methods) can display to you aspects of their personality.  Conversely, your actions might affect their personality, albeit not directly.

Why would we not want direct access to these properties though?  Often times, bugs can be created by accidentally changing the state of object properties.  By requiring public actions to access or change these properties we can avoid this class of errors.  This might require more code, but helps shield us from ourselves at times and allows us to program both freely and with restraint.

Next up is inheritance.  Much like inheritance of animals, inheritance of objects is the idea that one object is a sub-type of another.  We might for example want to draw shapes.  If we define an object called Polygon and have all other shapes inherit from it, we can reduce the amount of code necessary.  The idea is that while a Triangle object is not exactly a Polygon object, perhaps it shares much of the same code or that a Polygon object can define methods and properties that can be extended to other objects like Triangle.  Imagine for example that the Polygon object has one property, a list of points in space that determine vertices, as well as two methods, draw shape and get area.  You can imagine from this that the Triangle would be able to use those same properties and methods.  The list of vertices might have a different number of elements and the draw method might have to do things slightly differently but they are shared functionality between the parent Polygon object and the child Triangle object.  However, getting the area varies from Polygon to Polygon and that leads us to polymorphism.

The idea of polymorphism is a bit interesting.  It took me a long time to really understand why it's useful and why I should care about it.  Instead of trying to define it, as I'm not sure I really can, I'll continue my example about shapes.

Since the area of a Polygon requires a different calculation for each different convex polygon (yes, I've been assuming convex polygons all along), we can't sanely call a Polygon's get area method and expect a good response right?  That's where polymorphism comes in.  Imagine this situation, written in pseudo-Java:

Polygon polyA = new Triangle( [ (0,0), (0,1), (1,0) ] );
Polygon polyB = new Square( [ (0,0), (0,1), (1,0), (1,1) ] );

RealNumber polyAarea = polyA.getArea();
RealNumber polyBarea = polyB.getArea();

Rationally, it would makes sense that polyAarea is equal to .5 and polyBarea is equal to 1.  Assuming the get area methods were written well, this is the actual outcome.  Notice carefully that polyA and polyB are both Polygons though and yet their get area methods can turn out correct (there are no type errors).  This happens because polyA calls Triangle's get area method and polyB calls Square's get area method.  And that is the idea of polymorphism.  More formally, it's the idea that a parent class can define methods that can be used to simplify the logic of code by only requiring knowledge of the base classes methods.  In this case, since we need area and we know that all Polygons have a get area method, we can define our objects as Polygons and let the idea of polymorphism solve which get area method we really want to use.

I know that this is a lot of information and honestly it's a lot of stuff that I still don't completely grasp.  However, despite its criticisms, OOP is an integral part to most of the programming done in the world and I hope that if you intend to take on programming as either a hobby or a trade, that you took something away from this post.  In later posts, maybe Coding 102?, I'll go into real code examples to better reinforce all three of these ideas.  Until next time.

--CsMiREK


No comments:

Post a Comment