SEF9 - 43 Encapsulation in Object Oriented (OO) software design

(D) ENCAPSULATION in Object Oriented Software Design
==========================================================

(1) Encapsulation is the process of enclosing, as like putting things in a capsule, with the idea of protection.

(2) So far, everything we did in Part 3A, Part 3B and Part 3C for "person()" and "personsex()" classes is "public", meaning we allowed all our class attributes (variables) to status "read and write" by external users, that is, by client programs like client1.py and client2.py. We need to think about protection, and in object oriented languages, there are terms like "public", "private" and "protected" to protect both our attributes (variables) and methods (functions).

(3) Generally, encapsulation is used to refer to two(2) types of activities:

(3.1) providing protection mechanisms for restricting access to some of the object's components,

(3.2) creating code constructs that bundled data with the methods operating on that data.

The two(2) activities in Item(3.1) and Item(3.2) above are actually related, and most software implement a combination of both types.

(4) The ideas about encapsulation for attributes are about:

(4.1) protection from reading of data attributes,

(4.2) protection from writing of data attributes,

(4.3) protection from both reading and writing of data attributes,

While the ideas about encapsulation for methods are about protection from access to class methods and executing the class methods.

(5) Encapsulation is not totally about information hiding, as most people would say. Encapsulation is about controlling access on both attributes and methods in the class. For example, for class attributes, we have "read only" access and "read and write" access. There is no such thing as "write only" access because we can always "overwrite" whatever is current, and we know (can see) what we have "overwritten". For class methods, we either have "execute access" or "no access" like "Sorry, you nave no access to this method".

(6) A generic structure for a typical class in OOP is broken into sections as follows:

CLASS
... INHERITS .... PARENT CLASSES etc

PUBLIC ATTRIBUTES
...
...
PRIVATE ATTRIBUTES
...
...
PROTECTED ATTRIBUTES
...
...
PUBLIC METHODS
...
...
PRIVATE METHODS
...
...
PROTECTED METHODS
...
...

(7) For example, if we consider the "object" created by the class to be a "house", then everything on the porch or balcony of the house is considered exposed (PUBLIC), while everything internal to the house is considered restricted (PRIVATE and PROTECTED).

(8) In addition to the above general structure, for a typical concrete (executable) class, there are two(2) special methods called, a constructor() and a destructor().

(8a) A constructor() method is basically an operation that gets executed automatically when an object is created (instantiated) from the class, like when an external client program creates a new object. The constructor() normally executes the initialization operations for setting the initial values of the class attributes and/or for executing some startup methods inside the class.

(8b) The destructor() method is called when the program finished its execution. It is designed to properly remove the object from computer memory. This memory cleaning is called "garbage collection". Some programming languages provide automatic garbage collection while some do not. Most programming languages provide options for both. It is up to the software designer to decide on their use.

(9) How do we implement protection in a class? Easy. Programming languages have special "reserved words" for specifying attributes and methods to become public, private and protected. The methods used in these languages can be different but they carry the same similar intentions and meanings. You can search the internet for coding standards or conventions on Java classes or C++ classes. For example, Google for the phrase "High Integrity C++ Standards", or "Safe and Secure Programming in Ada". Look for the word "class" when you find the said documents.

As examples,

(9a) In Python, anything with two(2) leading underscores is private.

__self.EyeColor ==> private attribute
__self.Weight ==> private attribute

__run__(self,speed) ==> private method
__setID__(self,inputID) ==> private method

(9b) In Python, anything with one(1) leading underscore is semi-private.

_timeWait ==> semi-private attribute
_inhead ==> semi-private attribute

(9c) In Python, everything else outside of Item (9a) and Item (9b) above is considered public. We usually use semi-private attributes for storing values of intermediate calculations. I do not know about the use of semi-private methods because for all practical purposes, we either make the methods completely public or completely private, nothing in-between.

(10) For public attributes, we can get access directly using the "dot.notation" or through defined interfaces for these public methods, like the set-get methods we use in Part 3A and Part 3B. For public methods, there is no issue at all because they are meant for public access anyway. We must just follow exactly the rules for the defined interfaces for these public methods.

(11) Setting attributes and methods as public, private or protected is a design decision. There are no hard and fast rules about it in software construction. It is a good idea however, to follow the coding standards and guidelines for the particular programming language that we use. Search the internet with Google on phrase "List of Software Coding Standards".

(12) The normal practice in OOP is to restrict external access to all attributes by setting them as private. Thus, an external user cannot change the values of the attributes directly using the "dot.notation". To "read and write" values of these private attributes, the external user must go indirectly, that is, by using internal public methods (inside the class) like the "get-set" methods implemented in Part 3A and Part 3B. By going indirectly, we can write codes in our internal public methods that capture inputs and catch any unwanted errors that comes with the request. We are in control because we write the codes for our internal public methods. In essence, we still allow changes (and we want it) but we are in control because those changes can only be affected through our own written public methods. We do not allow those external codes to directly change our internal attribute values, because by doing so we are not in control of what resulting values may end up in our attributes. It may cause havoc when our attributes hold erroneous values.

(13) The Application Programming Interfaces (API) is a very important concept for encapsulation. The basic idea is that every action any external program needs to request an object to perform (interact with the object) can only be conducted via the defined interfaces of the object. The external interfaces to the object are the object's public methods. No other way. In object oriented programming, these "object-to-object" or "program-to-object" interactions are conducted via "message-passing". It is simple like, "Give me a message of what you want me to do, I will check whether it is allowable or not, then I will act on it appropriately. If it is allowable, I will act on it and return the results, and/or send with it a 'success' message. Otherwise, I will send you an error message and tell you the causes of the errors, etc". The Application Programming Interfaces (API) is really the documentation information that tells in details to the external user, for example, on how to call the object's public methods, what are the required inputs, what are the data types of the inputs, what are the maximum and minimum values of the inputs, the format and arrangement order of the inputs, what are the pre-conditions that must be satisfied before calling the method, bla bla bla etc.

(14) It is very important to note that by allowing external programs to access the object only through the object's published API, we have implemented encapsulation through information hiding. We hid from the external program many things. For example, the external program will not know how many variables (attributes) we used inside our object to do the computations and processing. In addition, the external program will also not know how the computations and processing are conducted (its algorithm). As far as the external program is concerned, "I give you an input, you just act on it and/or give me the outputs. Do not forget to also return to me a message, hopefully, a success message." This kind of "transaction" is very useful, especially that the external program do not care how we do it internally. We hid our internal details. We just need to maintain our interactions through rules of the Application Programming Interfaces (API).

(15) By hiding the internal details and exposing only the Application Programming Interfaces (API), we can achieve the following:

(15.1) Class Methods ==> When we need to improve our computations and processing methods, we revise and change our internal codes without the need to change the interfaces to it. The external program still interacts with our object in the same way via the same interface. That means, the external program does not need to change its existing codes. The old program will just continue to work seamlessly with our new codes, that is, as long as the external program use our object's public methods following strictly to the published Application Programming Interfaces (API).

(15.2) Class Attributes ==> We are free to add or change the internal attributes without messing up the entire computations and processing, and the external program does not need to know about this. We can change large parts of your classes without affecting their use by the external program, as long as the external program strictly obey the published Application Programming Interfaces (API).

(16) You can see an example of encapsulation in "people.py" class, that is accessed by an external program, the "client3.py". The "people()" class is actually the same "person()" class, except with modifications that made some private attributes and some private methods. Prior to this, everything in the old "person()" class is public.

===========================================================


--
WASSALAM
wruslan.hahaha

Attachments:
client1.py
client2.py
client3.py
people.py
Slides-Lecture-OOP-in-Python.pdf

Full Version with Microsoft Word Version and Attachments
Return to Software Engineering Fundamentals (SEF9MMUWRY)
Previous Topic: 42 Polymorphism in Object Oriented (OO) software design
Next Topic: 44 TUTORIAL on creating classes in the SVT system.(TUE 23 JULY 2013)

0 comments:

Post a Comment