Kenneth Ismert
kismert at gmail.com
Fri Feb 8 15:18:19 CST 2013
All, Here is a quick conceptual introduction to OO that I wrote. It takes a bottom-up approach to explaining classes and objects. -Ken PROGRESSION OF OBJECT PROGRAMMING PART 1: FROM GLOBAL TO SIMPLE CLASS An easy way to understand classes and objects is to understand what came before, and go through a broad progression of programming trends, with the goal of highlighting some of the motivations that drove the move to classes. 1) The Global Mess ================== Global routines. Global variables maintain state. Implementations: Machine code and assembler, early languages like FORTRAN, mid-level languages like C Advantages: a) Easy to get started. Simple to understand at first. Problems: a) Fragile, prone to errors when some code somewhere unexpectedly modifies global state, causing a chain of hard-to-debug unintended side-effects and crashes. b) As the program grows, the ability to understand and maintain it declines, and instability increases. 2) Simple Encapsulation ======================= Modules with private module-level variables. Functions allow outside code to get and set variables. Clear delineation between the public and private parts of a module. Implementations: Early high-level languages: Basic, Pascal, mid-level languages like C Advantages: a) Code reuse across many projects -- each module can cleanly contain a well-defined set of related functions. b) Private module-level variables ensure no code outside the module can directly affect the module's state. c) Using functions to get/set state allows breakpoints and easier debugging. d) Getter and setter functions control state access. Removing the setter makes a private variable read-only to outside code. No getter or setter makes the variable completely invisible. Problems: a) You have to think more about the organization of your code. b) Refactoring and reorganizing become significant tasks as you make your code more generic and abstract. c) No good way to handle multiples of a thing. d) Initializing a module's state can be tricky. 3) Simple Classes ================= Class modules as templates for Object instances. Formal naming of object parts and concepts. Object lifetime management by reference. Implementations: Smalltalk, VB 4 and later, C++, JavaScript, Python, etc..., anything with 'Object' in the name, or prefixed with 'O' Advantages: a) Much more fine-grained control over program state. b) You can easily manage multiple instances of things that require their own individual state. c) Initialization and shutdown are much easier. d) Classes allow you can leverage the power of abstraction to a much greater degree than previously possible. Problems: a) Organizing your code can become much more of a challenge. You are now forced to manage systems and patterns of classes, and the interactions between them. b) Abstraction can become a diversion from the real job of getting stuff done. c) Without discipline, classes can become an invitation to over-complication. The Basics ---------- Class The base module is renamed a Class, and becomes a template for making objects. Object An object is an instance of a class. Each object has its own, independent state. Member Variables Private module variables are separated from the module and given to the object. Each object instance gets its own set of member variables, allowing it to maintain its own state. Properties The ubiquitous getter and setter functions get their own special names and syntax. Properties enforce state access, but they are simply functions with another name. Methods The actions a class can perform on one of it's object instances. Methods are nothing more than the public functions and subroutines defined in the class. Calling a method typically modifies an object's state. Properties, being functions, are technically methods, but are usually treated separately. Setup/Shutdown -------------- Initialization The class can allow initialization code to be run when an object instance is created. Termination The class can also allow termination code to run when an object is destroyed. Object Creation and Lifetime ---------------------------- Possibly the most involved part of basic OO programming is how objects get created and destroyed, and how multiple instances of an object are maintained. I give just the basic concepts here: Reference Variables A new object is assigned to a variable when it is created. This reference variable refers to the independent set of member variables of an object instance. The reference also binds the object to its parent class, so you can call the proper methods for the object. How this is done varies from language to language. Object Lifetime References determine the lifetime of an object, just like an integer variable reference determines the lifetime of the integer value it refers to. Object lifetime is managed using some form of reference counting. Reference Counting An object remains 'alive' as long as it has one or more references to it. When an object has no references to it, it gets destroyed. You add references by assigning one object variable to another, or passing the object to a function. References are removed when an object variable goes out of scope at the end of a function, or when you explicitly destroy them in your code.