Who does this thing? Does it have any benefit? If I do this, my boss will think that I am wasting my time or making excuses to not work. Have these thoughts ever come to your mind when you were desperate to properly design your next software?
It is also possible that you have tried designing a software before, but you found that it's just time-consuming and it has no benefits. But throughout your career, you have these recurring thoughts that I should learn what are design patterns, how should I master MVC and that one day I will design something that is reusable, modular, and easy to read.
In this post, I will cover the basics about how you can properly design your next software even if you have failed last time.
What Will You Learn?
- Why your last design attempt failed?
- How to handle your manager/boss when you wanted to design?
- How will you succeed in designing?
- What is software development process?
- What is object-oriented analysis?
- What is object-oriented design?
- What are design patterns?
- And anything in between that is confusing you
What Will You Not Learn?
- You will not learn the syntax of Java, C# or C++
- You will not learn the difference between functions and variables
- You will not be overwhelmed with a list of design patterns
- You will not learn object oriented programming here
What? (you might say after reading the last line) No object oriented programming, then why am I wasting my time here. This post is about object-oriented design, but not programming. We all know about object oriented programming, i.e., how to write a class in C# and create an object or extend a class and you know through your experience that this is not helpful.
As one quote says, “Knowing how to hold a hammer does not make you an architect”. True? Similarly, learning Java programming will not make you a good software engineer (or software programmer or developer or software architect).
During the initial years of my undergraduate programs, I thought about designing is equal to writing an algorithm because I did not study about object oriented programming. Later, when I learnt about object-oriented programming, I thought one can conquer the world if one just learned everything that is there in 1000 pages of Dietel and Dietel book.
But that was not the case. I could not write a program without tearing my hair apart. I also notice that if I opened my program again after 6 months, it looked like such a mystery that even Sherlock Holmes could not solve it.
Then in the 4th semester, I learned about object-oriented analysis and design as a subject. But unfortunately, the focus was on UML modeling. I thought that UML is a cool thing -- you just generate some diagrams and hand them over to developers and they will come up with code using your designs (which will make you proud).
Even there was an option in the UML modeling tool that our class was using at that time and that tool can automatically generate the code from your UML class diagrams. What a beauty, now I design using UML models and then generate code, compile that code and ship it to a customer and get rich like Bill Gates. Awesome.
Afterwards, reality sets in, I was never able to generate such designs which are modular, easy to extend and easy to understand (The code which was generated from these tools was never compiled since UML tool only generates stubs). Then a period of chaos started.
Later in my undergraduate study, I learned subjects related to software engineering, software architecture, software process models and software project management. But I was unable to fit all things together until very late.
Still, I see people struggling with these concepts and are unable to fit the things together. They are overwhelmed with unstructured data available to them. One key to comprehending all this information is to involve yourself in a project. The only output for that project should be a software which your users can use.
In this post, I will share some basic object oriented analysis and design principles, practices and my experiences which you can use in your next project.
Introduction to Software Development Process Models
We all use some process or steps to develop a software. The simplest process model that I use is that I just write 6 lines on the back of a paper and call them feature list and then open Visual Studio and start writing code. This is it. A process model which I used during my college years.
I write my first commercial software (which is only used by 1 user and he abandoned that later) using Visual Basic 6.0 in my 2nd year of college using this process model.
There are many software development process models which I have studied and have applied in many projects.
One process model (which is scolded by many authorities) is waterfall process model. These are the steps in waterfall process model: Requirements gathering, analysis, design, implementation, and testing.
The problem with the waterfall process model is that you do all the things in the same exact sequence as it is written above. First, all the requirements are collected from the customers. A team analyzes requirements, documents and prepares specifications for the design team. The design team then develops the design using the specification and hands over the design to the implementation team. The implementation team writes code with respect to the design. Finally, test team tests the software against the specifications.
Everything is done sequentially and a lot of time is spent (months and even years) before the final product is shipped to the customer. Statistics tell us that when a product is shipped to the customer using waterfall process models, a huge number of customers denied taking that product because it did not meet their requirements.
You may have heard this jargon “Customer is always right”. This truly applies to software development as if the customer does not like the final product then all the effort (months and years) is wasted.
To cater to this problem, there is another philosophy which is called the iterative and evolutionary development. Based on this philosophy, there are many software development process models. Some examples are Scrum, extreme programming(XP) and Rational Unified Process. They are also known as agile development processes.
The concept of iterative development is simple. Software development is organized into a series of small projects called iterations. Each iteration has its analysis, design, implementation, and testing. At the end of each iteration, the customer input is taken. If a customer did not agree, then the loss is minimal (usually weeks) as compared to waterfall process model.
Now you understand the basic difference between iterative and sequential process models. Many organizations now use iterative development process models. The key idea is to minimize the waste(months vs weeks).
Why I Need to Understand Process Models
For a long time, I believe that designing a software is something like that: I design everything in the beginning and then using this design start coding, compile and then hand over the running software to the end user.
It turns out that this is not the best approach. You will have to change your design and your design evolves over time. Therefore incremental and evolutionary process model is important to understand. A flawless design is a myth. After subsequent iteration, one may realize that his or her initial design sucks.
Another point is that one should not design for all the requirements at the beginning. One should make a detailed design for the iteration on which one is working.
Therefore, the key takeaway is that you should use an iterative development process and complete design is not done at the start of the project. Similarly, whatever you design is not perfect and will be changed or evolved during the lifecycle of the project.
Object Oriented Analysis and Design-- Most Needed Definitions
When I developed my first project, which I developed using VB 6.0, I was disappointed in myself. This is because a single change in a small proportion of the code propagated to all other parts of the software.
The reason was that I didn't know about how to write modular code. Although it is possible to write modular code in a procedural language (VB 6.0 was procedural), it was difficult and not supported inherently in VB 6.0.
It was a nightmare to develop a simple software with only 4 features. It was terrifying to make any changes in the code because I didn't know about object oriented programming.
The solution to this problem is object oriented programming. This enables me to write modular programs. Before explaining how OOP and OOAD helped me out, first let’s discuss the difference between process and a development methodology.
Difference between Development Process and Development Methodology
Development methodology is something within the process. Examples of development methodologies are structured programming, object oriented and service oriented programming.
Development process defines a set of steps to carry out software development activities. Examples of software development processes are waterfall process, rational unified process, Scrum and extreme programming. Generally, you can pick any process methodology and then adopt any development methodology within that process.
One important benefit of object oriented methodology which no one tells you is that: you have the ability to design using real-world terms or domain specific terms. For example, if you are working on a software related to banking services, then you can use terms like Account, Ledger, Balance Sheet within the software code (as Names or attributes of classes).
How is this beneficial? You can design the software like real systems in the real world work. This makes it easy for you to update, modify and communicate with the customers. Hence object-oriented analysis is about identifying opportunities where you can represent real-world objects in the software world.
The first step in object oriented analysis is listening to a customer story and writing it down. A story is a description of customer pains and gains in his own words. Your job is to solve these customer pains and/or help the customer to achieve positive gains.
There can be more than one customer stories. You can tackle one or two user stories in a single iteration. But do not tackle more than 10 percent of all the stories in a single iteration. The next step is to design the domain model from user stories.
To design domain model, one simple technique that I used over time is reading the user story and underlining the nouns. These nouns are potential candidates for classes in your domain model. Domain model simply describes the names of the classes and/or attributes of the classes. A domain model does not describe any implementation detail such as function within a class.
In summary, there are two steps:
- Writing down user stories
- Designing the domain model
Demonstration of this will be shown in the upcoming example.
It’s quite easier to look at an object and say “yeah, it is a collection of variables”. Let me share a personal story: once I refactored a piece of code and designed a separate class which consisted of two primitive types. The funny thing was that another developer cheered me for developing a new variable.
There are many developers around who think like that. That is creating a class means creating a new variable. This is not the reason people use object oriented methodology. If you just want a collection of variable names, then you can use
struct in C language (which is a not an object oriented programming language).
Object-oriented design is about how your objects collaborate with each other. Here, you will decide who will create which objects and how they will interact to fulfill the needs of a user story.
The most import thing about analysis is identifying the domain classes from user story and the most important thing in object oriented design is identifying the collaboration between the objects to satisfy the user story.
In addition to designing the collaboration, there are principles and patterns which are followed by the software community. Gang of four patterns is extensively used in software designing but these patterns deserve another post (I will soon share with you and my personal story of my journey to design patterns).
If you are new to designs, then don’t get overwhelmed by all these pattern things. Just focus on one or two principles in the start. Then extend your learning towards more principles and design patterns.
What Are the Most Important Principles You Should Start With?
Don’t get overwhelmed with principles and design patterns. My suggestion is to focus on few principles and design patterns you are comfortable with in the start and then develop from there.
An important principle that I found very useful and I suggest that you should use is that:
“Prefer composition over inheritance”.
That is avoid using inheritance whenever possible. Use composition in any situation wherever you think inheritance is the answer.
Also, if you have never used interfaces in your code, then start using interface from today. This will enable you to write reusable and modular software.
Apply these two principles and in the upcoming weeks and you will realize the power of object-oriented analysis and design.
Advantages of Object Oriented Analysis and Design
With these principles and knowledge of object oriented programming, I was able to write a software which was modular and easy to read. Also, if I open the code today which I wrote 10 years ago, I can easily understand and I can easily update the code.
Here is a simple example which depicts a simple process for object oriented analysis and design.
First, I will share a user story that we will tackle in this example:
- A customer arrives at checkout with items to purchase
- Shopkeeper at counter greets and start a new sale
- Shopkeeper enters all the items
- System calculates the order total and taxes
- Customer pays
- System printed the receipt and updates inventory
Steps for Object Oriented Analysis
There are three steps in the following order:
- Identify class names
- Identify attributes
- Identify associations
Now I suggest that you underline all the nouns in the text of user story which you think will be good candidates for class names in our code.
Here are all the names of the classes that I can think of by reading the user story above:
You can see in the diagram that it is not developed using any UML tool. Just using a pen and rough sheet of paper. More than 60 percent of my designing is done using either a paper or a whiteboard.
Next steps: identifying attributes and associations. An attribute is what defines a class or object. An attribute can be an Id, amount or anything that can be measured. Association defines a relationship between classes and objects about how a class is connected to another class.
The following diagram shows the attributes and associations for the class diagram that I have shown above:
Domain Model with Attributes and Associations
Steps in Object Oriented Design
After analysis, we moved to object oriented design and here are the steps:
- Draw sequence diagram(s) for each scenario
- Draw design class diagram
- Apply design principles and software design patterns
A sequence diagram is used to show the message passing between objects of classes. It is the most important tool in object oriented design since it helps in designing the behavior of objects involved in a software.
Here is the sequence diagram that I draw to address the user story:
This sequence diagram shows the messages and the ordering in which they are sent among the objects to complete the objective of a user story.
From the sequence diagram, we can easily come up with design class diagram. A design class diagram is the last artifact that I usually create before diving into code.
It is very easy to draw design class diagram from the sequence diagram. Just write down the methods names in the classes where the arrow is pointing. For example,
GetItem() message is going from
Sale Class to
Item Class. Therefore,
item class will contain the
Design Class Diagram
After design class diagram, we can apply principles of object oriented design and design patterns, but I will put up another post for applying design patterns and principles.
From here, we can move to coding and start coding.
This is a very simple example to depict the process. For a real-life and real world object oriented analysis and design example, you can check out this link.
Summary Up to Now
Up to now, you have learned what is software development process, software development methodology and the differences between them. Why object-oriented analysis and design are more important than object oriented programming. You learned steps, techniques, and purpose for object oriented analysis and object-oriented design.
You also learned from a simple example how you can start properly designing the software using basic but most important principles and techniques.
Why Your Last Design Attempt Failed?
Many developers have attempted to design a software project properly but have failed or could not continue. Therefore, I have put together a list of problems or misconception about object-oriented analysis and design and how to tackle them.
If You Just Learn How to Design Perfectly
Perfect design at the start of the project is a myth. Your design will evolve, change, be corrected and modified over time. Many people think that they have to design perfectly at the beginning and then consider that design document as a sacred scripture. The truth is no one can come up with a perfect design at the start.
Software design is a heuristic process. It's something that you update over the lifetime of your project. There is no formula that you can use to produce best object oriented design every time. It involves trials and painful errors from which you can learn and then apply these learnings to your future projects.
You Have To Do Complete Analysis and Design Before Coding
Many developers and students believe that analyzing all requirements and all designing should be done before coding starts and during construction, one cannot change or extend it.
This is not true. If during coding, a team or developer realizes that the design can be extended or reduced, then it should be.
Similarly, when working in iterative development, usually 10 percent of all the requirements are tackled during one iteration. Therefore, you have to design for only 10 percent of all the requirements or user stories. If you have 10 user stories, then tackle one most important story (as indicated by the customer) in the first iteration and design for that only.
You Have to Give Enough Time to Design
When I started taking interest in object oriented design seriously, I was expending weeks on designing and thinking about coming up with a perfect and complete design. But during coding, things did not work out as they were supposed to be and I was disappointed.
The rule of thumb is that you should not give more than one day for a three-week iteration. I only give 2 to 4 hours before jumping to code. It does not mean you cannot go back to design for a couple of hours during construction. You can meet with your teammates and discuss design decisions during construction as well.
You Believe UML (Unified Modeling Language) is Everything
If someone told you that UML modeling is everything and recommends some expensive CASE (Computer Aided Software Engineering) tool, then you should come and look at my journal. Most of my designs never get to a CASE tool that our company has. When designing in teams, we use whiteboards and take a picture of them and then post these pictures in the project directory.
I believe design is not something that you draw using beautiful boxes of colors and properly align them. A rough diagram on paper is as effective as a diagram drawn using a CASE tool. OOAD is about getting a big picture and communication with your peers and with yourself when you are writing the code.
UML is just a tool that you used to translate your design ideas and which can be shared with other developers. Simply learning UML will not make you a good designer.
You Have to Apply All the Patterns and Principles
If you know about all the object-oriented design principles and patterns, then you might have realized that you want to apply all of these principles and patterns before moving to construction. If you do this, then you will not be successful. Use the principles and patterns according to the situation or problem at hand and you will be able to design a good software.
I suggest you should develop your own priority list of patterns and principles that you have fully understand. Then, apply these patterns according to the problem that is in front of you.
You Don’t Know How to Handle Your Boss / Manager
It is possible that your boss may resist while you come up with the idea of object oriented analysis and design. In your boss' eyes, it looks like an additional task which will not add any lines of code to your software. Also, it is also possible that your boss is not from a programming background and will not realize the importance of OOAD. Hence, there are some ways through in which you can manage your boss.
There are two kinds of bosses:
- Quality driven
- Schedule driven
Identify what influences your boss or manager. If your boss is quality driven, then you can show him the benefits about how an object oriented analysis and design can help him achieve the better quality features like modularity, readability, and reliability.
If your boss is schedule driven, then the first thing that you can do is show him that analysis and design activity will not take much time (only 2-8 hours in a 3 weeks iteration). You can also show him other time-saving benefits such as a good design can save time later in the project such as when you have to update or change some feature of a software.
Write what you like about the post in the comments section. Also, write about what you wanted to learn as I intend to write a few more articles soon on this subject? You can visit www.objectorienteddesign.org for a small free report that I have put together for you.
- 31-October-2016: Update
- Added UML diagrams and source code for all the classes involved in the sample example
- Removed critical spelling and grammar mistakes