Click here to Skip to main content
15,885,729 members
Articles / Programming Languages / Java

Dependency Inversion principle (DIP)

Rate me:
Please Sign up or sign in to vote.
0.00/5 (No votes)
23 Jul 2012CPOL 9K   3  
Depend explicitly, require explicitly, but only require what you really need.

SOLID principles:

Depend explicitly, require explicitly, but only require what you really need.

Consider an example (not for production, illustrative purposes only):

Java
public class ConsoleLogger {
  public static void log(String text)  {...}
}

public class SomethingDoer {
  public void doSomething() {
    // I won't show you the code      
  }
}

Is there a connection between SomethingDoer and Logger? You'll never know unless you have a code for SomethingDoer. OK, I'll show you:

Java
public class SomethingDoer {
  public void doSomething() {
    ConsoleLogger.log(new Date().toString());
  }
}

This may not look that bad as long as you have the code. But what if this SomethingDoer is in a 3rd-party library and it sends some stuff to the console while you don't want it? The solution is to explicitly say: "SomethingDoer depends on Logger". Here is a possible solution:

Java
public class ConsoleLogger {
  public void log(String text)  {...}
}

public class SomethingDoer {
  private final ConsoleLogger logger;

  public SomethingDoer(ConsoleLogger logger) {
    this.logger = logger;
  }

  public void doSomething() {
    logger.log(new Date().toString());
  }
}

Logger logger = new Logger();
SomethingDoer somethingDoer = new SomethingDoer(logger);

In this code, you just can't make an instance of SomethingDoer without giving it an instance of Logger. But still, what should we do in case we don't want any output at all? SomethingDoer doesn't basically require any particular logger, it requires something that IS a logger, but no further details are required. So, here's the next step:

Java
public interface Logger {
  void log(String text);
}

public class ConsoleLogger implements Logger {
  public void log(String text) {...}
}

public class NullLogger implements Logger {
  public void log(String text) { /* do nothing here */ }
}

public class SomethingDoer {
  private final Logger logger;

  public SomethingDoer(Logger logger) {
    this.logger = logger;
  }

  public void doSomething() {
    logger.log(new Date().toString());
  }
}

// if we want to enable output:
Logger logger = new ConsoleLogger();
SomethingDoer somethingDoer = new SomethingDoer(logger);
somethingDoer.doSomething(); // got output

// if we want to disable output:
Logger logger = new NullLogger();
SomethingDoer somethingDoer = new SomethingDoer(logger);
somethingDoer.doSomething(); // no output

In future posts, I'm going to cover this topic in more detail.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
Software Developer (Senior)
Russian Federation Russian Federation
This member has not yet provided a Biography. Assume it's interesting and varied, and probably something to do with programming.

Comments and Discussions

 
-- There are no messages in this forum --