Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Clean Code

Clean Code

Slides for presentation I gave at Equal Experts client in New York.


April 11, 2016

More Decks by anildigital

Other Decks in Programming


  1. Clean Code
    Anil Wadghule

    View full-size slide

  2. – Martin Fowler
    “Any fool can write code that a computer can
    understand. Good programmers write code that
    humans can understand.”

    View full-size slide

  3. Kent Beck’s Design Rules
    • Runs all the tests

    • Expresses all the design ideas that are in the
    system / Reveals intention

    • Contains no duplication

    • Minimises the number of entities such as classes,
    methods, functions, and the like / Fewest elements
    (Remove anything that doesn’t follow
    rst 3)

    View full-size slide

  4. Software Entropy
    • The Broken Window

    • Don’t leave code with broken windows.

    View full-size slide

  5. Clean Code: A Handbook of Agile Software Craftsmanshi

    by Robert C. Martin

    View full-size slide

  6. Names
    • Use intention revealing names

    int d; // elapsed time in day

    • Instead use

    int elapsedTimeInDays;

    View full-size slide

  7. Use Intention revealing
    • See this

    // BAD
    public List getThem() {
    List list1 = new ArrayList();
    for (int[] x : theList)
    if (x[0] == 4) list1.add(x);
    return list1; ‚Àè
    • After changing names and magic numbers

    // GOOD
    public List getFlaggedCells() {
    aggedCells = new ArrayList();
    for (Cell cell : gameBoard)
    if (cell.isFlagged())

    View full-size slide

  8. Use pronounceable names
    • If you can’t pronounce it, you can’t discuss it

    class DtaRcrd102 {
    private Date genymdhms;
    private Date modymdhms;
    nal String pszqint = "102";
    /* ... */

    • better this way

    class Customer {
    private Date generationTimestamp;
    private Date modi
    nal String recordId = "102";
    /* ... */

    View full-size slide

  9. Use searchable names
    • Make this searchable

    • MAX_CLASSES_PER_STUDENT is more searchable
    than 7

    • Avoid encoding

    • AccountImpl

    • IShapeFactory

    • Do not add unnecessary pre
    xes, like pre
    xing name of
    the project before every class

    View full-size slide

  10. Naming consistency
    • Classes and objects should be nouns

    • Manager, Generator, Processor

    • Method names should start with verbs

    • isValid(), getUsername();

    View full-size slide

  11. Naming consistency
    • Pick one word per concept (No synonyms)

    • Don’t mix concepts

    • Don’t be cute

    • Don’t pun

    • Use Solution Domain Names (Programmer friendly)

    • Use Problem Domain Names (Domain friendly)

    View full-size slide

  12. Scope Rule
    • Smaller the scope of the variable smaller the

    • Larger the scope of the variable larger the

    View full-size slide

  13. Small functions
    • Functions should be small

    • 4 to 5 lines are good.

    • More than 10 lines is big.

    • Smaller functions are easy to understand.

    • Large functions are less reusable.

    • Large functions may include functionality that belong in different classes.

    • Large functions may hide the classes.

    • Smaller well named functions in well named classes will make it easier to
    navigate the code

    View full-size slide

  14. Small functions
    • Instead of adding a comment on a code
    block, extract it into a method with name same
    as the comment.

    • Minimise number of local variables.

    • Minimise indentations in a method.

    • Do one thing.

    View full-size slide

  15. Same level of abstraction
    • All the statements in a function should be at one level of

    void compute() {


    ags|= 0x0080;


    • If the statements are not at one level of abstraction extract
    them in functions with meaningful names.

    • Functions having one abstraction level are likely to do one

    View full-size slide

  16. Command Query Separation
    • Function should either do something or answer
    something, doing both is confusing

    View full-size slide

  17. Function arguments
    • Keep the function arguments to the minimum. Usually
    less than 3 variables.

    Circle makeCircle(double x, double y, double radius);

    Circle makeCircle(Point center, double radius)

    • Avoid boolean parameters.

    doMakeResponse(context, request, true

    • Avoid passing in nulls or returning nulls.

    • Use objects or maps when you need many arguments.

    View full-size slide

  18. Argument objects
    Circle makeCircle(double x, double y, double radius)

    Circle makeCircle(Point center, double radius);

    View full-size slide

  19. The Stepdown Rule
    • Reading code from Top to Bottom

    • Follow Stepdown rule

    View full-size slide

  20. Switch cases

    View full-size slide

  21. Switch cases
    • Functions with switch statements are likely to do
    N things.

    • Switch cases are likely to get scattered
    throughout the code.

    • Open ended switch violates OCP.

    View full-size slide

  22. Example
    • Consider this method of Bird class:

    double getSpeed() {
    switch(type) {
    case EUROPEAN:
    return getBaseSpeed();
    case AFRICAN:
    return getBaseSpeed() - getLoadFactor() * numberOfCoconuts;
    return (isNailed) ? 0 : getBaseSpeed(voltage);


    View full-size slide

  23. Polymorphism
    abstract class Bird {
    abstract double getSpeed()

    class European extends Bird {
    double getSpeed() {
    return getBaseSpeed();
    class African extends Bird {
    double getSpeed() {
    return getBaseSpeed() - getLoadFactor() * numberOfCoconuts;
    class NorwegianBlue extend Bird {
    double getSpeed() {
    return (isNailed) ? 0 : getBaseSpeed(voltage);
    European African

    View full-size slide

  24. When switch statements are
    • When there is no possibility of more cases.

    • When switch is used for creation of Polymorphic
    objects. Like in a Factory.

    • When switch cases are managed locally and
    can not scatter throughout the system.

    View full-size slide

  25. Class / Object

    View full-size slide

  26. Objects
    • Objects should hide their internal structure.

    • Follow ‘Tell Don’t Ask’ (Law of Demeter).

    • Avoid train wrecks - Don’t ask.

    ((EditSaveCustomizer) master.getModelisable()

    • Instead tell the object to perform task


    View full-size slide

  27. Classes
    • Classes should be small.

    • Small classes follow Single Responsibility
    Principle (SRP).

    • Avoid God classes. (Avoid doing everything with
    single class)

    • The class should be cohesive.

    View full-size slide

  28. Cohesion
    • Classes should have a small number of instance

    • More variables a method manipulates the more
    cohesive that method is to its class.

    • The more cohesive the methods are the more
    cohesive the class will be.

    • We want the classes to have high cohesion.

    • When classes lose cohesion, split them!

    View full-size slide

  29. SOLID Principles
    • SRP — Single Responsibility Principle

    • OCP — Open Closed Principle

    • LSP — Liskov’s Substitution Principle

    • ISP — Interface Segregation Principle

    • DIP — Dependency Inversion Principle

    View full-size slide

  30. Single Responsibility
    • A class should have only one reason for change

    View full-size slide

  31. Open Closed Principle
    • A class should be easy to extend without

    View full-size slide

  32. Liskov’s Substitution
    • Subclasses mustn’t change expected behaviour

    View full-size slide

  33. Interface Segregation
    • Interfaces shouldn’t force classes to implement
    useless methods

    View full-size slide

  34. Dependency Inversion
    • High level and low level code should depend on

    View full-size slide

    • Explain yourself in code

    // Check to see if the employee is eligible for full bene

    if ((employee.
    ags & HOURLY_FLAG) && (employee.age > 65))
    // or this?
    if (employee.isEligibleForFullBene

    View full-size slide

    • Comments represent bad code.

    • If you need comments to understand what the
    code is doing then the code is poorly written

    View full-size slide

  37. — Brian W. Kernighan and P. J. Plaugher
    “Don’t comment bad code—rewrite it.”

    View full-size slide

  38. Accepted comments, but
    not always!
    • Legal comments

    • Informative comments e.g. warning comments

    // format matched kk:mm:ss EEE, MMM dd, yyyy
    Pattern timeMatcher = Pattern.compile

    "\\d*:\\d*:\\d* \\w*, \\w* \\d*, \\d*


    • TODO comments

    • Javadocs in Public API

    • For ampli

    View full-size slide

  39. Good comments
    • Explanation of intent

    public void testConcurrentAddWidgets() throws Exception {

    //This is our best attempt to get a race condition
    //by creating large number of threads.
    for (int i = 0; i < 25000; i++) {
    WidgetBuilderThread widgetBuilderThread = new
    WidgetBuilderThread(widgetBuilder, parent);
    Thread thread = new Thread(widgetBuilderThread);



    View full-size slide

  40. Bad comments
    • Mumbling

    public void loadProperties()
    String propertiesPath = propertiesLocation + "/" + PROPERTIES_FILE;
    FileInputStream propertiesStream = new FileInputStream(propertiesPath);
    catch(IOException e)
    // No properties
    les means all defaults are loaded

    View full-size slide

  41. Formatting
    • Good formatting code is important

    • Follow code style of your organisation. If not
    present, create one.

    View full-size slide

  42. Exception handling
    • Use exceptions instead of returning error codes.

    • Use unchecked exceptions

    • Provide context with exceptions.

    • Don’t return null

    • Don’t pass null
    Clean code is readable, but it must also be robust.

    View full-size slide

  43. Code smells
    • Long method

    • solution - Extract method into many smaller auxiliary methods

    • Large class

    • solution - Apply single responsibility principle

    • Duplicate code

    • Too many parameters

    • Comments

    • …

    View full-size slide

  44. Clean tests
    • One Assert per Test

    • Single Concept per Test

    public void testAddMonths(){
    SerialDate d1 = SerialDate.createInstance(31, 5, 2004);

    SerialDate d2 = SerialDate.addMonths(1, d1);

    assertEquals(30, d2.getDayOfMonth());

    assertEquals(6, d2.getMonth());

    assertEquals(2004, d2.getYYYY());


    View full-size slide

  45. Clean Tests - FIRST
    • Fast

    • Run quickly

    • Independent

    • should not depend on each other

    • Repeatable

    • ability to run tests in any environment

    • Self-validating

    • should have boolean output, either pass or fail

    • No need to manually check the logs

    • Timely

    • Unit tests should be written just before the production code that makes them pass

    View full-size slide

  46. Refactoring
    • Don’t afraid of changing code to make it better

    • Always leave the campground cleaner than you
    found it. — The Boy Scout Rule

    • Refactor when tests are green (Apply TDD)

    • Follow DRY

    View full-size slide