SOLID — From Zero To Potato 5
About Dependency Inversion Principle (DIP) in this article ,this will be last article about SOLID.
Today I will continue explain about Dependency Inversion Principle (DIP) in this article.We will be familiar about others principle in SOLID because even if we don’t know about SOLID principle we can learn from our senior’s code, various medium article and tutorials, but you will be very rare to hear what is Dependency Inversion and how should we used it and why we should use.
By the way, if you are already working as Android Developer don’t confuse with Dependency Injection. You will be already familiar with popular libraries Dagger,Hilt and Koin. These two are very different so be careful when you explain especially in interviews.
Dependency Injection is an implementation technique for populating instance variables of a class. Dependency Inversion is a general design guideline which recommends that classes should only have direct relationships with high-level abstractions.
Dependency Inversion Principle (DIP): High-level modules should not depend on low-level modules; both should depend on abstractions.
Let me explain you with simple code implementation, after that you will be more understand about DIP. As usual let start with Student
class that has a dependency on a Teacher
class to perform some functionality:
class Student(private val teacher: Teacher) {
fun askQuestion(question: String) {
teacher.answerQuestion(question)
}
}
In above example the Student
class depends directly on the Teacher
class, violating the DIP because a high-level module (Student
) is depending on a low-level module (Teacher
).
so let refactor to adhere to the DIP, we can introduce an abstraction between the Student
and Teacher
classes:
interface QuestionAnswerer {
fun answerQuestion(question: String)
}
class Teacher : QuestionAnswerer {
override fun answerQuestion(question: String) {
// answer the specified question
}
}
class Student(private val questionAnswerer: QuestionAnswerer) {
fun askQuestion(question: String) {
questionAnswerer.answerQuestion(question)
}
}
In this refactored version, we introduce an abstraction called QuestionAnswerer
that the Student
class depends on instead of the Teacher
class directly. The Teacher
class implements the QuestionAnswerer
interface, and the Student
class now depends on the interface rather than the concrete Teacher
class.
This adheres to the DIP because the Student
class is now depending on an abstraction (QuestionAnswerer
) rather than a concrete implementation (Teacher
). This allows for greater flexibility and extensibility, as any class that implements the QuestionAnswerer
interface can be used as a dependency for the Student
class, not just the Teacher
class.
After seeing the refactored version, i hope you will get why we should use Dependency Inversion too, DIP helps to decouple the components in your application and can make your code more flexible, maintainable, and easier to test.
Thank you for taking the time to read this article. I hope that my writing has been informative and thought-provoking. Happy coding for all you then before.
Previous Article about SOLID :
Single Responsibility Principle (SRP) : https://medium.com/arpalar-tech/solid-from-zero-to-potato-e7b5cfe8c7a1
Open/Closed Principle (OCP): https://medium.com/arpalar-tech/solid-from-zero-to-potato-2-5a4c17bd8ec8
Liskov Substitution Principle (LSP): https://medium.com/arpalar-tech/solid-from-zero-to-potato-3-94d6f63dbbfe
Interface Segregation Principle (ISP): https://medium.com/arpalar-tech/solid-from-zero-to-potato-4-d1d9b42c3a78