Clean Code
Pranjut Gogoi
Senior Software Consultant
Knoldus Software LLP
What is clean code ?
Agenda
● Meaningful Names
● Functions
● Comments
● Classes
Meaningful Names
●
Intention Revealing Names
int d; // elapsed time in days
int elapsedTimeInDays;
public List<int[]> getThem() {
– List<int[]> list1 = new ArrayList<int[]>();
– for (int[] x : theList)
– if (x[0] == 4)
– list1.add(x);
– return list1;
– }
Questions
● 1. What kinds of things are in theList ?
● 2. What is the significance of the zeroth
subscript of an item in theList ?
● 3. What is the significance of the value 4 ?
● 4. How would I use the list being returned?
Answers
public List<int[]> getFlaggedCells() {
List<int[]> flaggedCells = new ArrayList<int[]>();
for (int[] cell : gameBoard)
if (cell[STATUS_VALUE] == FLAGGED)
flaggedCells.add(cell);
return flaggedCells;
}
Avoid Disinformation
XYZControllerForEfficientHandlingOfStrings
XYZControllerForEfficientStorageOfStrings
“Avoid disinformation” = “similar name with
different spelling”
Make Meaningful
Distinctions
● (a1, a2, .. aN)
public static void copyChars(char a1[], char a2[]) {
for (int i = 0; i < a1.length; i++) {
a2[i] = a1[i];
}
}
Use Pronounceable Names
class DtaRcrd102 {
private Date genymdhms;
private Date modymdhms;
private final String pszqint = "102";
/** */
};
class Customer {
private Date generationTimestamp;
private Date modificationTimestamp;;
private final String recordId = "102";
/* ... */
};
Use Searchable Names
for (int j=0; j<34; j++) {
s += (t[j]*4)/5;
}
int realDaysPerIdealDay = 4;
const int WORK_DAYS_PER_WEEK = 5;
int sum = 0;
for (int j=0; j < NUMBER_OF_TASKS; j++) {
int realTaskDays = taskEstimate[j] * realDaysPerIdealDay;
int realTaskWeeks = (realdays / WORK_DAYS_PER_WEEK);
sum += realTaskWeeks;
Avoid Mental Mapping
● Avoid i, j, k
● Be a professional programmer than a smart
programmer
Class names & Method Names
● Class Name should be a Noun
● Method name should be a verb
● Don't be cute with names
Pick One Word per Concept But
don't pun
● For Fetching use only fetch, not retrieve and
get
● Don't pun means don't use add for inserting a
record into the database and adding two
numbers as well.
Domain Names and meaningful
context
● Use domain problem and solution names
● Don't use technical names
● Prefix or suffix for context
Functions
● Small
● Do one thing
● Use Descriptive Names
● Function Arguments
● Have No Side Effects
● Command Query Separation
● Don’t Repeat Yourself
● Structured Programming
Function Arguments
● Niladic is best, Monadic is better, Dyadic is good,
Triad is bad and Polyadic is worst
● Common Monadic Forms : when input gets
changed in the function
● Flag Arguments are ugly.
● Dyadic Functions
● Triad
● Argument Objects
Have No Side Effects
public class UserValidator {
private Cryptographer cryptographer;
public boolean checkPassword(String userName, String password) {
User user = UserGateway.findByName(userName);
if (user != User.NULL) {
String codedPhrase = user.getPhraseEncodedByPassword();
String phrase = cryptographer.decrypt(codedPhrase, password);
if ("Valid Password".equals(phrase)) {
Session.initialize();
return true;
}
}
return false;
}
}
Comments
“Don’t comment bad code—rewrite it.”
Comment practices
● Comments Do Not Make Up for Bad Code
● Explain Yourself in Code
if ((employee.flags & HOURLY_FLAG) &&
(employee.age > 65))
Or this?
if (employee.isEligibleForFullBenefits())
● Good Comments
● Bad Comments
Good Comments
● Legal Comments – for copyright and authorship
● Informative Comments
// format matched kk:mm:ss EEE, MMM dd, yyyy
– Pattern timeMatcher = Pattern.compile(
– "d*:d*:d* w*, w* d*, d*");
● Explanation of Intent
● Warning of Consequences
● TODO Comments
● Javadocs in Public APIs
Bad comments
● Mumbling
●
Redundant Comments
●
Misleading Comments
● Mandated Comments
● Journal Comments
●
Noise Comments
●
Position Markers
●
Closing Brace Comments
● Commented-Out Code
●
Too Much Information
Classes
● Variables at the beginning
● Keep class small
● Keep name for determining the responsibility
● Name should be able to described in 25 words.
● Single Responsibility Principle
● Cohesive
● Interfaces and abstract classes
Unit Test
●
1st
law: You may not write production code until
you have written a failing unit test.
●
2nd
law: You may not write more of a unit test than
is sufficient to fail, and not compiling is failing.
●
3rd
law: You may not write more production code
than is sufficient to pass the currently failing test.
● Unit tests are not second class citizen
● Its even more important than the architecture.
What makes a clean test?
● Ans: Three things. Readability, readability, and
readability
● Readibility = clarity, simplicity, density of
expression
● FIRST = Fast Independent Repeatable Self-
Validating Timely
Thank you !!!

Clean code

  • 1.
    Clean Code Pranjut Gogoi SeniorSoftware Consultant Knoldus Software LLP
  • 3.
  • 4.
    Agenda ● Meaningful Names ●Functions ● Comments ● Classes
  • 5.
    Meaningful Names ● Intention RevealingNames int d; // elapsed time in days int elapsedTimeInDays; public List<int[]> getThem() { – List<int[]> list1 = new ArrayList<int[]>(); – for (int[] x : theList) – if (x[0] == 4) – list1.add(x); – return list1; – }
  • 6.
    Questions ● 1. Whatkinds of things are in theList ? ● 2. What is the significance of the zeroth subscript of an item in theList ? ● 3. What is the significance of the value 4 ? ● 4. How would I use the list being returned?
  • 7.
    Answers public List<int[]> getFlaggedCells(){ List<int[]> flaggedCells = new ArrayList<int[]>(); for (int[] cell : gameBoard) if (cell[STATUS_VALUE] == FLAGGED) flaggedCells.add(cell); return flaggedCells; }
  • 8.
  • 9.
    Make Meaningful Distinctions ● (a1,a2, .. aN) public static void copyChars(char a1[], char a2[]) { for (int i = 0; i < a1.length; i++) { a2[i] = a1[i]; } }
  • 10.
    Use Pronounceable Names classDtaRcrd102 { private Date genymdhms; private Date modymdhms; private final String pszqint = "102"; /** */ }; class Customer { private Date generationTimestamp; private Date modificationTimestamp;; private final String recordId = "102"; /* ... */ };
  • 11.
    Use Searchable Names for(int j=0; j<34; j++) { s += (t[j]*4)/5; } int realDaysPerIdealDay = 4; const int WORK_DAYS_PER_WEEK = 5; int sum = 0; for (int j=0; j < NUMBER_OF_TASKS; j++) { int realTaskDays = taskEstimate[j] * realDaysPerIdealDay; int realTaskWeeks = (realdays / WORK_DAYS_PER_WEEK); sum += realTaskWeeks;
  • 12.
    Avoid Mental Mapping ●Avoid i, j, k ● Be a professional programmer than a smart programmer
  • 13.
    Class names &Method Names ● Class Name should be a Noun ● Method name should be a verb ● Don't be cute with names
  • 14.
    Pick One Wordper Concept But don't pun ● For Fetching use only fetch, not retrieve and get ● Don't pun means don't use add for inserting a record into the database and adding two numbers as well.
  • 15.
    Domain Names andmeaningful context ● Use domain problem and solution names ● Don't use technical names ● Prefix or suffix for context
  • 16.
    Functions ● Small ● Doone thing ● Use Descriptive Names ● Function Arguments ● Have No Side Effects ● Command Query Separation ● Don’t Repeat Yourself ● Structured Programming
  • 17.
    Function Arguments ● Niladicis best, Monadic is better, Dyadic is good, Triad is bad and Polyadic is worst ● Common Monadic Forms : when input gets changed in the function ● Flag Arguments are ugly. ● Dyadic Functions ● Triad ● Argument Objects
  • 18.
    Have No SideEffects public class UserValidator { private Cryptographer cryptographer; public boolean checkPassword(String userName, String password) { User user = UserGateway.findByName(userName); if (user != User.NULL) { String codedPhrase = user.getPhraseEncodedByPassword(); String phrase = cryptographer.decrypt(codedPhrase, password); if ("Valid Password".equals(phrase)) { Session.initialize(); return true; } } return false; } }
  • 19.
    Comments “Don’t comment badcode—rewrite it.”
  • 20.
    Comment practices ● CommentsDo Not Make Up for Bad Code ● Explain Yourself in Code if ((employee.flags & HOURLY_FLAG) && (employee.age > 65)) Or this? if (employee.isEligibleForFullBenefits()) ● Good Comments ● Bad Comments
  • 21.
    Good Comments ● LegalComments – for copyright and authorship ● Informative Comments // format matched kk:mm:ss EEE, MMM dd, yyyy – Pattern timeMatcher = Pattern.compile( – "d*:d*:d* w*, w* d*, d*"); ● Explanation of Intent ● Warning of Consequences ● TODO Comments ● Javadocs in Public APIs
  • 22.
    Bad comments ● Mumbling ● RedundantComments ● Misleading Comments ● Mandated Comments ● Journal Comments ● Noise Comments ● Position Markers ● Closing Brace Comments ● Commented-Out Code ● Too Much Information
  • 23.
    Classes ● Variables atthe beginning ● Keep class small ● Keep name for determining the responsibility ● Name should be able to described in 25 words. ● Single Responsibility Principle ● Cohesive ● Interfaces and abstract classes
  • 24.
    Unit Test ● 1st law: Youmay not write production code until you have written a failing unit test. ● 2nd law: You may not write more of a unit test than is sufficient to fail, and not compiling is failing. ● 3rd law: You may not write more production code than is sufficient to pass the currently failing test. ● Unit tests are not second class citizen ● Its even more important than the architecture.
  • 25.
    What makes aclean test? ● Ans: Three things. Readability, readability, and readability ● Readibility = clarity, simplicity, density of expression ● FIRST = Fast Independent Repeatable Self- Validating Timely
  • 26.

Editor's Notes

  • #10 Don&amp;apos;t use a, an, the Zork in a class and thezork in a class
  • #11 New programmer came and Mohomd bla blac Modi blabla
  • #14 Class names not Manager, Processor, DATa, Info Yes = Customer, WikiPage, Account Whack() instead of kill() EatMyShorts() instead of abort()
  • #16 AccountVisitor = in technical it represents the visitor pattern. AddFirstName Context = address
  • #17 Structure programming = So if you keep your functions small, then the occasional multiple return , break , or continue statement does no harm and can sometimes even be more expressive than the sin-gle-entry, single-exit rule. On the other hand, goto only makes sense in large functions, so it should be avoided. How Do You Write Functions Like This?
  • #18 Arguments renderForSuite() and renderForSingleTest() . Instead of render(true) Dyadic = assertEquals(expected, actual) Traid = assertEquals(message, expected, actual)
  • #19 Session.initialize(); creates problem Output Arguments
  • #22 Legal comments = ide hides it for us Explanation of Intent = for the logic behind something, why we have chosen this logic. Warning of Consequences = we do not need it now, but in older days when junit was not there we should had it.
  • #23 Mumbling = necessary comments are not sufficient Redundant Comments = head before a function which takes more time to read than the function itself. Mandated Comments = silly to have javadoc for every funciton… it has all function arguments and its description…...we have done that in primoris and its aweful … Journal Comments = journal entry of changes Noise Comments = a comment without any meaning Position Markers = // Actions ///////////////////////// Closing Brace Comments = if{} //if while{} //while
  • #24 Make it small from the beginning Not like lets make it big first then we will divide it
  • #26 Duplicate code not expected Meaningful variables FIRST = F - fast I – independent of each other R – repeatable in QA prod, dev S – return boolean T = timely wirte unit test