Writing Quality Code

33
“Writing Quality Code” By Indika Maligaspe Give a man a fish and you feed him for a day Give a man a fish and you feed him for a day Teach him how to fish and you feed him for a lifetime” Teach him how to fish and you feed him for a lifetime”

description

Most developers write code to fulfil a business requirement, however the cost of project is not decided by the development but by the effort maintenance. So the emphasis should be to write quality , clean code that minimizes time spent on maintenance.

Transcript of Writing Quality Code

Page 1: Writing Quality Code

“Writing Quality Code”By Indika Maligaspe

““Give a man a fish and you feed him for a dayGive a man a fish and you feed him for a dayTeach him how to fish and you feed him for a lifetime”Teach him how to fish and you feed him for a lifetime”

Page 2: Writing Quality Code

Intro...Intro...

Indika Maligaspe

K. Indika Maligaspe

Developer, Designer, Architect , Trainer

Tech Geek specialized in JAVA and .Net

Over 14 years if experience in IT / Web Technologies

Lover of almost all sports... http://www.linkedin.com/profile/view?id=201732082&trk=nav_responsive_tab_profile

Page 3: Writing Quality Code

ContributorsContributors

David Bernstein Alan Shalloway Steve McConnell Martin Fowler Gamma, Helms, Johnson, Vlissides (GoF) James Coplien

Page 4: Writing Quality Code

Seminar AgendaSeminar Agenda

What effects Software Quality? How to accommodate change? What are Code Qualities? Principles vs. Practices Principles of Coding (Rules of Thumb)

Organizing Principles Clarity Principles (good practices)

Summary Q&A

Page 5: Writing Quality Code

What effects Software Quality?What effects Software Quality?Two questions…..Two questions…..

• How many of you have been involved inHow many of you have been involved in

A totally successful project? A totally failed project? A "challenged" project?

Page 6: Writing Quality Code

What effects Software Quality?What effects Software Quality?Two questions….. Two questions…..

• When Adding FunctionalityWhen Adding FunctionalityWhere was the Problem?Where was the Problem? Is it writing the new code? Is it integrating it into the system?

Why?

Page 7: Writing Quality Code

How can we design to How can we design to accommodate change? accommodate change?

We are not trying to anticipate change, per se, as much as writing our code to accommodate change better. Trying to anticipate change can lead to “paralysis by analysis”

To do this we need A way to avoid change when possible (outside of the scope of this

document) Componentized Architectures (CBA / SBC etc…) Use of Design Patterns Agile concepts

A way to make change less risky when one cannot avoid it Code clarity and maintainability Refactoring

Page 8: Writing Quality Code

What are Code Qualities?What are Code Qualities?

• A computer has no concept of "well-written“ source code. However, from a human point of view source code can be written in a way that has an effect on the effort needed to comprehend its behavior.

• Many source code programming style guides, which often stress readability and usually language-specific conventions are aimed at reducing the cost of source code maintenance by having code predictability.

Page 9: Writing Quality Code

PredictabilityPredictability

We can’t predict how our requirements are going to change

However we can predict how our code will adapt to unpredictable requirement changes

How can we increase our predictive abilities?

Pay attention to code quality

Page 10: Writing Quality Code

Six Code QualitiesSix Code Qualities

Cohesive Correct Coupling Non Redundant Encapsulated Testable Assertive

Page 11: Writing Quality Code

Principles vs. PracticesPrinciples vs. Practices

Principle A standard Theory

Practice How you put a principle to practice

i.e.

Principle - The need to be clean

Practice - Wash hands

Page 12: Writing Quality Code

CohesionCohesion

Cohesion refers to how “closely the operations in a routine [or class] are related ” (Code complete – Steve McConnell)

Strong cohesion is related to clarity and understanding.

No "schizophrenic classes” No “10000 - line classes” No “10‐page methods"

Page 13: Writing Quality Code

Good Strong Good Strong cohesioncohesion

Class Cohesion - A class has a single responsibility, and everything in the class is about fulfilling that responsibility.

Using design patterns and OO concepts (strategy / encapsulation / open – close etc…)

Method Cohesion - Each method is about fulfilling one functional aspect of the classes responsibility.

Programming by intention can help us to code with better method cohesion from the beginning

Page 14: Writing Quality Code

Class Cohesion - exampleClass Cohesion - example

+PKIencrypt()+PKIdecrypt()+PGPencrypt()+PGPdecrypt()+sendMessage()+getInputStream()+getOutputStream()

Socket

UDPSocket TCPSocket

Class cohesion will be covered in detail in future sessions

+sendMessage()+getInputStream()+getOutputStream()

Socket

+encrypt()+decrypt()

Encryption

PKIEncryption PGPEncryption

1

*

UDPSocket TCPSocket

using Stratergy Pattern

Page 15: Writing Quality Code

Method cohesion – programming Method cohesion – programming by intentionby intention

public Socket(String actionType) { // Add code to read data through the socket and get a input stream System.out.println("Socket.java - Getting InputStream"); if (1 == (Integer.parseInt(actionType))) { // Add code to do PKI encryption System.out.println("Socket.java - PKI encrypting"); } else if (2 == (Integer.parseInt(actionType))) { // Add code to do PKI decryption System.out.println("Socket.java - PKI decrypting"); } else if (3 == (Integer.parseInt(actionType))) { // Add code to do PGP encryption System.out.println("Socket.java - PGP encrypting"); } else if (4 == (Integer.parseInt(actionType))) { // Add code to do PGP decryption System.out.println("Socket.java - PGP decrypting"); } else if (5 == (Integer.parseInt(actionType))) { // Add code to do GZip compression System.out.println("Socket.java - GZip compression "); }

}

}

Page 16: Writing Quality Code

Method cohesion – programming Method cohesion – programming by intentionby intention

public Socket(String actionType[]) { this.socketInputStream = getInputStream(); this.socketOutputStream = getOutputStream(); doEncryption(Integer.parseInt(actionType[0])); doDecryption(Integer.parseInt(actionType[1])); doCompression(Integer.parseInt(actionType[1])); }

private InputStream getInputStream() { // Add code to read data through the socket and get a input stream System.out.println("Socket.java - Getting InputStream"); return null; }

private OutputStream getOutputStream() { // Add code to write data through the socket and get a output stream System.out.println("Socket.java - Getting OutputStream"); return null; }

private void doEncryption(int encryptionType) { if (1 == encryptionType) { doPKIEncryption(); } else if (2 == encryptionType) { doPGPEncryption(); } }

PrivateMethods

SergeantMethod

Page 17: Writing Quality Code

What “programming by intention” What “programming by intention” will bringwill bring

Method cohesion Cohesion of perspective

Sergeant is the controller (very little implementation)

Private’s do the work (implementation)

Ease of refactoring Ease of applying/forming design patterns Easier to test

Page 18: Writing Quality Code

CouplingCoupling

Coupling refers “to the strength of a connection between two routines [or classes] Coupling is complement to cohesion. Cohesion describes how strongly the internal contents of a routine [or class] are related to each other. Coupling describes how strongly a routine is related to other routines. The goal is to create routines [and classes] with internal integrity (strong cohesion) and small, direct, visible, and flexible relations to other routines [and classes] (loose coupling).”*

Tight coupling is related to highly interconnected code

* Code Complete Steve McConnell 1993 p 22 Copyright

Page 19: Writing Quality Code

Correct CouplingCorrect Coupling

How interconnected Objects are Loosely coupled – Objects should be independent

and should mind their own business. One employee should not know about salary details

of other employees in the company

Tight coupled – Objects are interconnected and intertwined. Change one place and “All hell breaks loose”

Every employee knows the salaries of all the employees in the company. Give increment to one – MAJOR PROBLEM

Page 20: Writing Quality Code

Sample CouplingSample Coupling

Tight Coupling

Loose Coupling

Employee

+getSalaries() : Object

Company

1*

Employee

+getInstance() : Company+getSalary(in empNo : string) : long double

Company

* * +getSalarie(in empNo : long) : double

«interface»Employees

Page 21: Writing Quality Code

Types of couplingTypes of coupling

Identity One type to the fact that coupled another type exists.

Representational One type coupled to the interface of another.

Inheritance Subtypes are coupled to their superclass, in that any change in

the superclass will propagate downward. Subclass

One type coupled to the fact that there are subclasses to a type, and what specific subclasses exist.

Writing Quality code David Bernstein – 2008 p24 Copyright

Page 22: Writing Quality Code

No Redundancy – No Redundancy – Avoiding duplicationAvoiding duplication

"One Rule in One Place" Redundancy is not just:

Redundant state Redundant functions

It can also be redundant relationships, design, construction, etc… Anything that is redundant will cause maintenance problem

Page 23: Writing Quality Code

Avoid RedundancyAvoid Redundancy

The “once and only once” rule If you are going to copy and paste, ask yourself

What is the code I want to reuse? Can I make a new method that can be used by both my current

method and the place I need to use this similar functionality? If 2 entities need to do this, how likely will there be a third, fourth,

etc…

Writing Quality code David Bernstein – 2008 p27 Copyright

Page 24: Writing Quality Code

Encapsulation – Information hidingEncapsulation – Information hiding

Two commonly used encapsulation methods Data : The data needed for a class to fulfill it's responsibilities is hidden from

other entities

Implementation: How a class implements a particular function, or whether it implements it itself or delegates to other objects, is hidden

Not so commonly used Type: Abstract classes and interfaces can hide their implementing classes

Design: Assembling, collaborating classes with an object factory keeps clients decoupled from the way they are designed (abstract factory)

Construction: Encapsulation of construction means wrapping "new" in, at least, a separate method, giving you control over the return type (use of getInstance)

Page 25: Writing Quality Code

TestabilityTestability

Class responsibility should be individually testable (unit testing)

Considering how to test before developing or designing leads to Correctness Good OO design OO design patterns

And forces you to look at: the public method definitions what the responsibilities of the object are

Easy testability is achieved by strong cohesion, loose coupling, good encapsulation and non redundancy

Page 26: Writing Quality Code

Role of TestabilityRole of Testability

You should always do unit testing. It helps in code correctness

Whether you agree or not ask two things You should always ask “ How will I test my

design / code?” If you see that your code/ unit or design is not

testable, then there is something wrong in it. Ask your self “How can I make this more testable”

Page 27: Writing Quality Code

Assertive or InquisitiveAssertive or Inquisitive

In a relationship between two entities A and B Should A ask the state of B and then use it

(inquisitive) Should A tell B to do the task involving the

state (Assertive) It does not increase the code or design, just who

takes the code and responsibility Which is better?

Page 28: Writing Quality Code

Assertive vs. Inquisitive – Assertive vs. Inquisitive – which is better?which is better?

The more Assertive you code / design is the more decoupled you code or design is

Remember the “Gang of Four”: Design to interfaces. An object's state is generally a part of its implementation. We should not design to that, as it is highly likely to change

"He who holds the state should hold the function"

Favor Assertiveness over Inquisitiveness (tell but not Ask principle)

Page 29: Writing Quality Code

Organizing Principles

Cohesion is an organizing principle in that it helps us decide where new entities belong

Coupling is an organizing principle in that it helps us decide how different entities should talk to each other (the interfaces)

Eliminating redundancy is an organizing principle because it tells us to bring together redundant methods/rules into a single place

Page 30: Writing Quality Code

Clarity Principles How to document code

Implementation details (documentation) should be in the code, not as comments If you have to write comments explaining “names”, your naming conventions

might be having issues There is BIG difference between comments about “what” you are doing and

comments “why” (business rules) Conceptual information can often be documented in abstract classes and

interfaces Naming is not always easy. It is often a good idea to pair on naming issues Always format code properly

(refer http://tutorials.rezg.net/Java/CodeConventions.pdf ) Try not have more the

100 characters per line 30 lines in a method 30 methods per class

Page 31: Writing Quality Code

SummarySummary

Remember the Code QualitiesRemember the Code QualitiesT – TestabilityT – Testability

R – Non RedundancyR – Non Redundancy

E – EncapsulationE – Encapsulation

C – CohesionC – Cohesion

C – Correct CouplingC – Correct Coupling

A – Assertive A – Assertive

T.R.E.C.C.A. T.R.E.C.C.A. Writing Quality code David Bernstein – 2008 p54 Copyright

Page 32: Writing Quality Code

Summary – In a NutshellSummary – In a Nutshell

In order of importance Be testable Contain no duplication (once and only once) Loose coupling, strong cohesion and clarity

When writing, always program by intention Methods and classes should be implemented so they can be

understood totally from their names and their public interfaces. This flows naturally from up‐front testing, and decreases coupling

Classes should organize ideas in a readily understandable way Use intention‐revealing names so you don't have to explain

method, member or class names with additional comments Adhere to a coding standard

Page 33: Writing Quality Code

Thank YouThank You