Before going
directly in to the depth of c++, we will jus brush up some basic things related
to it. When I start teaching u C++, the first question arising from u will be
wats the use of C++ when U have a beautiful lang. like C in ur hands. To answer
this q I hav to start from the scratch. Scratch in the sense, s/w evolution.
The
growth of s/w systems can be compared to the growth of a tree. As u know tree
grows in layers. In the same manner s/w systems also grows in layers or I can
call it as diff phases. Each layer s built one after the other for the past few
decades, and each layer having some improvement over the other. Now since we
compared tree n s/w systems, let me tell u one thing, the only basic difference
in the growth of tree n s/w systems is that in tree only the outermost layer is
functional where as in s/w sys each n every layer continues to be functional.
Now
if am trying the sketch the schematic of this s/w evolution, it will like this
Machine
Lang.
↓
Assembly
Lang.
↓
Procedural
Lang.
↓
Object
model Lang.
We will be concentrating only on
object model languages, but to answer our prev q we will have to compare PL
with OO.
Procedural Lang:
Before
I start this let me tell u something. All this programming layers are jus a way
in which a given prog is organized and developed. It s not concerned with any
particular programming Lang.
In
general computer Lang deals with two concepts – data and algorithms. Data
constitutes the information a program uses and processes and algorithms are the
methods that the program uses.
Procedural
Lang emphasizes the algorithm side of programming. In proc Lang, each statement
in this prog tells the compiler to do something a prog in a proc Lang is a
set of instructions.
Now
consider I have a prog where in I have to get input, add and find the avg. of
the values and print the output. It’s a small prog n one person can easily sit
n type it without any difficulty. But as the complexity of the program
increases, difficulty in coding, maintaining and debugging also increases. For
eg: lets consider a real world eg. Lets say a washing machine program. Hope
everyone knows that our washing machine is running on a particular s/w. It is
having so many functionalities. For e.g.: spin, wash, temperature control etc.
Now a single person sitting and typing the entire code is not going to be that
feasible. He may code it. But debugging becomes a Herculean task. So procedural
language provides us with the flexibility of dividing / modularizing our entire
program into smaller independent units known as modules which can be handled by
individuals. And the object modules created separately will be linked together
at the end to get the real world solution.
Now as we know
for every good thing, we hav some bad things associated with it. In the same
manner in the above method also, even though it provides simplicity in working,
there are few disadvantages associated with it.
All this time
we were giving importance to the way in which the program is getting done n we
never thought about the data associated with the functions. In a large prog which
s split up in to functions, there will be some local data associated with each
function. At the same time, there will be some values which have to be kept
global so that it can be used by all functions present in that program. These
global data will be moving freely around the program. For eg: in the above
case, jus consider a weight variable which is declared as global variable. This
weight variable may need to get manipulated by spin and wash. But since it s a
global variable, even ur
temp_cntl module and other module have access over it.
The chances of
these data getting corrupted by any of these functions are very very large. So
at the end u might hav completed Ur big project without compile time errors but
the output u r getting won’t be the one what u want. ie) data corruption occurs
in the program. So instead of running for 40 kgs it may run for 20 or 140 kgs.
This data insecurity was considered as a major draw back in procedural languages
which made it not that suitable for real world application. .
Another problem
associated with procedural languages is here the code and data is kept apart or
in other words the code and data is not related. If I take C as an example for
a procedural language, in C language, units of code called functions and units
of data called structures are not formally connected even if the functions are
supposed to act on structures. A C function can operate on more than one type
of structure and more than one function can act on same structure which makes
us say that they are not related.
For eg :
consider a structure corresponding to a student.
struct Student
{
char Name[20];
int marks;
};
This structure will need some
functions to act up on it. As per C standards, we will be writing these
functions as global functions. Lets say
void
Add_Details(char *, int);
void
Calculate_Percentage();
Since we are modeling something
known as a student, we will expect the functions Add_Details(char*, int) and
Calculate_Percentage() to act on only the structure student and not on any
other real world model like teacher. But in our C language, we don’t have any
flexibility where in we can restrict these functions to act only on these
structures or vice-versa. This makes real world modeling very inefficient in
procedural approach.
These two major disadvantages forced
the development of next layer in the s/w evolution termed as object model
languages.
Object model languages;
Since in
procedural languages, the greatest disadvantage was the negligence of data, in
object model languages data was considered as a critical element in program
development. It binded data unit more closely with the functions or to the code
acting upon this data there by restricting the free flow of data around the
system. And this binded unit is termed as objects in object model languages.
|
The data of an
object can be accessed only by the member functions associated with the object
n objects can communicate with each other through member functions. The member
functions of one object won’t be able to access the data of another object.
This type of programming helps preventing data from getting corrupted by the
unnecessary intervention of other functions. So in OML, a real world problem is
visualized in terms of collection of objects communicating with each other.
Let’s talk a
little more in detail about all these concepts. As a software engineer, our
ultimate aim is to find a real world solution for a real world problem. As I
already told you, in OML, the real world solution we find will always be in
terms of collection of objects. We have already seen the technical or I should
say a very basic definition for objects. Ie_ a binded unit of data and
functions acting upon the data
But
when we do reverse engineering, to find a solution for the real world problem,
first we should know what are the things in the real world which can be
visualized as objects and what are the features of the objects which can be
considered as data and what are the features of an object which can be
considered as functions.
In
a real world problem, an object can be considered as an instance of a real
world entity (entity means something which has an existence). But the reverse
statement, ie) the instances of all real world entities are objects may not be
true. A real world entity can be considered as an object only if it has
1. an identity
2. a state
3. a behavior
Identity always refers to a
particular name / uniqueness of the real world entity which makes it distinct
from other entities. A state refers to an existing condition or position or a
particular thing of an entity and behavior corresponds to the set of actions
this entity can perform and which can sometimes result in change of one or more
states.
Let’s take a
real world example and explore the above mentioned things. Let’s say the real
world problem in my hands is “Car dealership
system” .
The first thing
we have to do here is , we need to get the exact problem statement. Ie) what
exactly does the system expects us to do. Let say, here the
Problem statement is :
“Design a website for the car dealership
system where in customer should be able to see different cars present with the
dealer and their entire details. He should also be able to have a virtual
driving experience with his own configuration of the car. Once he has decided
on the car, he should be able to do transactions for buying the car and
ultimately dealer should be able to keep in track of the orders made by the
customer.”
Once we have
the problem statement in our hands, the next step we should do is trace out the
real world entities which are interacting with the system. In this system, the
main three real world entities you can trace out is
- Car
- Customer
- Dealer
The next thing
is to trace out those functionalities or requirements related to the above real
world entity.
If you consider Customer, the
things / functionality he may want to do in the system is
1.
View the details of car present.
2.
Virtual driving experience
3.
Configure the car
4.
Buy the car etc
As far as dealer is concerned he
may want to
5.
Keep in track of the orders.
6.
Include / Exclude cars etc
As far as car is concerned, its
functionalities can be
7.
Start engine
8.
Apply accelerator
9.
Apply break
10. Switch
on / off ac etc
I am tracing out only few here.
Work with this, u will get more use cases.
Since we are going to solve this
problem using OML, we need to trace out those real world entities in this
system which are objects. Let’s take the example of car and let s see how to do
it.
Car :
We
are going to see if the real world entity called car have state, behavior and
identity so that we can consider it as an object. Sticking on to the definition
of states : states of a car can be
- Running state
- Stopped state
- Colour
- Seating capacity
- Model Name
- Engine number
If you stick on to the
definitions of behavior, we can see that the functionalities we listed can be
directly considered as the behaviors of car. Ie:
- Start Engine
- Applying accelerator
- Applying break
- Switch on / off ac etc
We know that technically object
is a collection of data and function. Usually
states traced out for the real world entity will be mapped into data of an
object and behaviors will be the functions.
Why I used to term mapped between
states and data is : data is something to which I can assign some value. But if
you see the states, we cannot assign values directly to some of the states. For
eg : running state and stopped state : I cannot assign a value directly to it. So
if I need to trace out those attributes
/ characteristic quality behind these states which can be considered as data.
For eg: for the above two states, I can consider the attribute behind it as
speed and mileage. So speed and mileage becomes data of car if ever car is
considered as an object. Because of this reason , the terms data and attributes
are used interchangeably. The other two states, colour and Model Name can be
directly considered as data.
Concentrating
a little more on the attributes : we can see that the attributes colour and
model name doesn’t change even when car performs an action. Usually we call
such states as static attributes. On
the other hand, the attributes speed and mileage gets changed when actions like
applying accelerator or switch on / off ac is performed. So we usually call
such attributes as dynamic attributes.
The above picture / structure is
just a blueprint or a frame work for each and every car constructed. Or I can
say it is a generalization of the concept of car. There will be thousands of
other cars in existence, all of the same make This blue print is termed as classes in OML.
So the above as we said is just a
plan. So when does a car come into existence. Only when we create an instance
of that plan right. and how do we identify between different car. By its
registration no. so lets say we have two car : ka 03 mh 6517 and ka 03 mh 9657.
So these no s is acting as an identity for the cars here and since they are
from the same plan, they will be having its own states and behaviors. So we
call these two cars as the objects here.
Ultimately we concluded that the
real world entity car can be mapped into an object.
We will be talking more about
classes and objects in our future classes. So lets go back to our OML. In OML,
every real world problem will be mapped to a collection of objects and classes.
Object model languages are
classified into two types.
- object oriented languages
- object based languages
For the time being just remember
the classification. Once we are done with the general introduction to OOP’s we
will come back to the difference between these two.
Object oriented languages :
As
we already learned, since OOP’s is part of OML, it is also based on classes and
objects. Now our aim is to find solutions for real world problems using object
oriented programming concepts. To ensure that the increasing complexity of s/w
systems are met, OOP’s strictly ensures that the programmers follow specific
design strategies / principles while using object oriented programming
techniques. In today’s class we are going to c what are the design strategies
to be followed in OOP’s.
The
basic design strategies are
- Abstraction
- Separation
- Establishing relationships.
Abstraction :
Abstraction is a
design technique that focuses on the essential aspects of an entity and ignores
or conceals less important or non-essential aspects. Abstraction is an
important tool for simplifying a complex situation to a level where analysis,
experimentation, or understanding can take place
Abstraction
is concerned with both the "attributes" and "behavior". As
we told before attributes refer to the properties or characteristics associated
with an entity. Attributes typically correspond to the data that is recorded
for an object. The "behavior" represents the set of actions that the
object can perform. An action usually corresponds to an action that the
real-world entity might perform.
Let’s
take the same car dealer ship system as an example and try to find what
abstraction is, based on that.
Let’s
take the entity Dealer. Dealer is a normal person in this real world. As a
person, he has an identity, a family genealogy, a medical history, a genetic
profile, a credit record, a set of talents, and many more. Similarly there is a
rich set of actions of which the dealer is capable (singSong, doDance,
haveChild, getSick, increaseCreditLimit, payBills, etc.). Trying to capture
even a small part of this enormous detail in a software object is pointless.
What is important is to capture those aspects of a "dealer" that are
relevant to the development of the car dealership system. This capturing of
aspects relevant to a particular application is termed as abstraction. So
showing the abstraction from the actual details diagrammatically :
So from the above abstraction, the attributes and the behaviour can be diagrammatically represented as below.
The structure of
abstraction shown above for the dealer can be considered as a blue print for
each and every sales person in that company. So we can call it as a class. A
specific member of this group, say john smith refers to the object of this
class.
It is important
to realize that a single entity may have many valid abstractions. While the
genetic profile of a salesperson is not relevant to a sales tracking system, it
may be relevant to a medical database system. This alternative abstraction is
shown in the figure below..
Abstraction is
vital to creating tractable software objects because the real-world objects are
far too complex to be captured in complete detail.
Visualizing the object /
abstraction is over. The next step is separation.
Separation:
Generally speaking,
separation refers to distinguishing between a goal or effect and the means or
mechanism by which the goal or effect is achieved. This is often stated as
separating "what" is to be done from "how" it is to be
done. This is not a term completely related to s/w. If you see your day to day
life, two words used in the same way is goal and plans. For eg: as a student
your goal is to get placed in an mnc. And the plan to achieve the goal is doing
hard work. Or in mechanical terms, we can use it as product and process and in
s/w terms we can use it as interface and implementation.
We
will be sticking on to the definition of separation as separating the interface
and implementation. The interface is
viewed as the visible, external aspect of the software that must be understood
to use the software. The implementation is viewed as the hidden, internal
aspect of the software that is important only to the implementor. It is this
form of separation that is considered as
the actual definition of separation.
Visible : interface
--------------------------------------------------------------------------------
Hidden : implementation
For eg: consider your lift. The
interface given to u is to press the necessary buttons to reach a particular
floor and how it is implemented internally is not known to us. Another eg is commands
like
read(f, buffer, nbytes). This is the
interface. The user knows that the
command is to transfer nbytes
of data from file f
to the specified buffer
. The mechanism required to
achieve this effect involves the disk hardware, software device drivers, the
file system, the disk block management code, and run-time I/O library routines,
none of which need be mentioned in the description of the read
command.
Interchangeability of Implementations
|
One interface
can have more than one implementations. For eg: a lift can be implemented
either using electricity or even using a battery. An implementation can be
considered as satisfying an interface, if the behavior defined by the interface
is provided by the implementation. This provides flexibility to implementers
because different implementations may satisfy the same interface. The several
implementations may differ in time or space efficiency, purchase price,
maintainability, documentation quality, reliability, or other non-functional
characteristics. If separation is fully observed, one implementation for a
given interface can be replaced by a different implementation of that interface
without altering the overall operation of the larger system of which it is a
part. The ability to associate different implementations with the same
interface is shown in the above figure.
Now talking
about separation in object oriented programming: abstraction and separation are
always talked together. In the beginning itself I was telling you that in an object,
data and the code which is acting on the data is binded together such that the
access to the data with in the objects is only through the code in that object.
Here implementation can be considered as the
data and the implementation of the methods hidden inside the object and
interface refers to signature of all methods visible outside the object.
The hiding of the object’s
implementation details is often termed as encapsulation. Or encapsulation refers to the restriction
of access to data within an object to only those methods defined by the
object's class
We have visualized class and
objects and we have separated our interface and implementation. Now, take any real
world entity. For eg : An eg is an aircraft system which consists of numerous
small systems. Aircraft is having a propulsion system, a control system,
navigation systems etc. you can c that it consists of different components
interacting together to achieve the behaviour of aircraft. The different components
refer to classes here. So the next step is to organize our classes such that it
represents a complex real world system. That s exactly what the next step is.
Establishing Relationships:
Now in our example, the whole system is made of numerous small components / entities. Let me list few among the different entites here.
Car
or different types of car and different components of car like Engine, Piston,
Radiator, Wheels, Ac, Stereo, Customer, Dealer etc.
Using
abstraction and encapsulation we have designed all the components individually.
To consider it as a whole system called car dealership system, all these
individual components have to work together in a co-operative manner. In terms
of implementation, to make them work together, we need to establish proper
relationships among the different components.
Lets
try to do it now.
- If you consider the relationship between car and customer, both of them related for a specific functionality called “buy”. In the same manner, dealer and car is also related for a specific functionality called “sell”. Here any change in the entity car is not going to have an effect on the so called customer or dealer. Such a relationship is termed as Association. Let me represent it diagrammatically as below.
Customer______________Car
Dealer________________Car
- If you consider the relationship between Car, Engine, Wheel and Car, Ac and Stereo, one thing you can notice here is both the categories hold a “has a ” relationship. ie) car has an engine or ca has a wheel and in the same manner car has an ac or car has a stereo. Or we can say that car is composed of engine, wheel, ac and stereo. Broadly we call such relationship as Aggregation. Again, if you consider the strength of relationship in the two categories, engine and wheel is having a stronger relationship with car than ac and stereo. Or in other words, the so called car doesn’t have any existence without an engine or wheel. This type of tightly coupled relationships are known as Composite aggregation. Where as Ac and stereo which is having a week relationship or loose coupling with car or which has standalone existence is said to have a Shared aggregation with car. Let me put it diagrammatically as below.
The
same composite aggregation holds good for engine, piston and radiator as shown above.
- If I consider Car and different types of car like racing cars, maruthi, Honda , Hyundai etc, we can say that racing car is a car or maruthi or Honda or Hyundai is a car. Or simply I can say that Car and the different types of car is having an “is a” relationship. It is more technically termed as generalization. Let me represent it diagrammatically as below.
- Finally let me consider one final entity, Racing road. As you know, racing road at some point may be flat or may have humps etc. Usually for Race cars, the parameter called suspension height (the distance between wheel and body) varies according to the type of the road. Ie) suspension height decreases if road is flat or it increases if the road has hump so that ground clearance (the distance between road and body..the lesser the ground clearance the more stable the vehicle) is always minimum. Keeping all these things in mind, I can say that Race Cars “uses” or “depends on” race roads or race tracks. Or more technically we can call it as dependency relationship. let me represent it diagrammatically as below. Racing Car-------------------------------------> Race Track
If you notice we
can see that dependency is very similar to association. How you have to
distinguish is, in dependency unlike association, the change in one entity will
cause a change in another entity. Here change in type of race track results in change in suspension height
of race car.
Now we have a
broad diagrammatic representation of the whole system in our hands. In our
future classes, we will technically implement all these things which we
mentioned theoretically.
Note:
In today’s class you can see
different notations used by me especially while discussing relationships. These
notations are part of something known as UML. Please go back and try to collect
some basic knowledge about UML and come back to tomorrow’s class. We will have
a chit chat on that in tomorrow ‘s class.
Reference :
OOAD : Grady
Booch
0 comments:
Post a Comment