Tìm hiểu nhanh SOLID thần thánh
solid
2
oop
19
Java
158
software design
2
White

Nguyễn Tuấn Anh viết ngày 23/01/2019

Trong bài viết này, mình sẽ giúp các bạn tìm hiểu nhanh SOLID thần thánh nhé :D

SOLID là năm nguyên lý cơ bản trong thiết kế phần mềm hướng đối tượng, giúp code trở nên dễ hiểu, linh động và dễ bảo trì hơn. Tác giả của SOLID là kỹ sư phần mềm nổi tiếng Robert C. Martin. Năm nguyên lý trong SOLID bao gồm:

  • S: Single responsibility principle
  • O: Open/closed principle
  • L: Liskov substitution principle
  • I: Interface segregation principle
  • D: Dependency inversion principle

1. Single responsibility principle

A class should have only a single responsibility.

Nguyên lý này có thể hiểu là một class chỉ nên đảm nhận một và chỉ một trách nhiệm duy nhất. Hay nói theo một cách khác, chúng ta chỉ nên viết và sửa đổi một class bởi vì một lý do duy nhất mà thôi. Nguyên lý giúp code dễ quản lý và bảo trì hơn.

Ví dụ:

Thay vì viết một class ôm đồm tất cả các công việc liên quan đến thao tác với CSDL như này:

class DBHelper {

    public Connection openConnection() {};

    public void saveUser(User user) {};

    public List<Product> listProducts() {};

    public void closeConnection() {};

}

Chúng ta nên tách thành các class con, mỗi class xử lý một công việc riêng kiểu như này:

class DBConnection {

    public Connection openConnection() {};

    public void closeConnection() {};

}

class UserHelper {

    public void saveUser(User user) {};

}

class ProductHelper {

    public List<Product> listProducts() {};

}

2. Open/closed principle

Software entities (classes, modules, functions, etc.) should be open for extension, but closed for modification.

Nguyên lý này có thể hiểu là nếu như có thêm yêu cầu phát sinh, chúng ta nên mở rộng/kế thừa các class đã tồn tại thay vì sửa đổi chúng.

Ví dụ: Lớp Staff được thiết kế chỉ để đóng gói các thông tin cơ bản của nhân viên. Nếu muốn bổ sung thêm nghiệp vụ quản lý cho nhân viên, chúng ta nên tách riêng một class Manager kế thừa class Staff, bởi vì không phải nhân viên nào cũng có nghiệp vụ quản lý.


3. Liskov substitution principle

Objects in a program should be replaceable with instances of their subtypes without altering the correctness of that program.

Nguyên lý này có thể hiểu là các đối tượng của class cha có thể được thay thế bởi các đối tượng của các class con mà không làm thay đổi tính đúng đắn của chương trình.

Ví dụ: Các đối tượng Square đều có thể xem là các đối tượng Rectangle.


4. Interface segregation principle

Many client-specific interfaces are better than one general-purpose interface.

Nguyên lý này có thể hiểu là thay vì viết một interface cho một mục đích chung chung, chúng ta nên tách thành nhiều interface nhỏ cho các mục đích riêng. Chúng ta không nên bắt buộc client phải implement các method mà client không cần đến.

Ví dụ:

Chúng ta có một interface Animal như sau:

interface Animal {

    void eat();

    void run();

    void fly();

}

Chúng ta có 2 class DogSnake implement interface Animal. Nhưng thật vô lý, Dog thì làm sao có thể fly(), cũng như Snake không thể nào run() được? Thay vào đó, chúng ta nên tách thành 3 interface như thế này:

interface Animal {

    void eat();

}

interface RunnableAnimal extends Animal {

    void run();

}

interface FlyableAnimal extends Animal {

    void fly();

}

5. Dependency inversion principle

Depend on abstractions, not on concretions.

Nguyên lý này gồm có 2 ý nhỏ:

  1. Các module cấp cao không nên phụ thuộc vào các module cấp thấp. Cả hai nên phụ thuộc vào abstraction.
  2. Abstraction không nên phụ thuộc vào detail. Detail nên phụ thuộc vào abstraction.

Ví dụ, chúng ta có 2 module cấp thấp BackendDeveloperFrontendDeveloper và 1 module cấp cao Project sử dụng 2 module trên:

class BackendDeveloper {

    private void codeJava() {};

}

class FrontendDeveloper {

    private void codeJS() {};

}

class Project {

    private BackendDeveloper backendDeveloper = new BackendDeveloper();
    private FrontendDeveloper frontendDeveloper = new FrontendDeveloper();

    public void build() {
        backendDeveloper.codeJava();
        frontendDeveloper.codeJS();
    }

}

Giả sử nếu sau này, dự án thay đổi công nghệ. Các backend developer không code Java nữa mà chuyển sang code C#. Các frontend developer không code JS thuần nữa mà nâng lên các JS framework. Rõ ràng chúng ta không những phải sửa code ở các module cấp thấp mà còn phải sửa code ở cả module cấp cao đang sử dụng các module cấp thấp đó. Điều này cho thấy module cấp cao đang phải phụ thuộc vào các module cấp thấp.

Lúc này, chúng ta sẽ bổ sung thêm một abstraction Developer để các module trên phụ thuộc vào:

interface Developer {

    void develop();

}

class BackendDeveloper implements Developer {

    @Override
    public void develop() {
        codeJava();
    }

    private void codeJava() {};

}

class FrontendDeveloper implements Developer {

    @Override
    public void develop() {
        codeJS();
    }

    private void codeJS() {};

}

class Project {

    private List<Developer> developers;

    public Project(List<Developer> developers) {
        this.developers = developers;
    }

    public void build() {
        developers.forEach(developer -> developer.develop());
    }

}

Tài liệu tham khảo

  1. https://en.wikipedia.org/wiki/SOLID

  2. https://dzone.com/articles/solid-principles-dependency-inversion-principle

Bình luận


White
{{ comment.user.name }}
Bỏ hay Hay
{{comment.like_count}}
Male avatar
{{ comment_error }}
Hủy
   

Hiển thị thử

Chỉnh sửa

White

Nguyễn Tuấn Anh

27 bài viết.
187 người follow
Kipalog
{{userFollowed ? 'Following' : 'Follow'}}
Cùng một tác giả
White
48 41
MyContact là một ứng dụng mà mình thường viết mỗi khi học một ngôn ngữ hay công nghệ mới. MyContact chỉ là một ứng dụng CRUD đơn giản, cho phép ngư...
Nguyễn Tuấn Anh viết gần 3 năm trước
48 41
White
27 14
Hướng dẫn lập trình Spring Security Trong bài viết lần này, mình sẽ giúp các bạn bước đầu tìm hiểu (Link) thông qua xây dựng các chức năng: Đăng ...
Nguyễn Tuấn Anh viết gần 3 năm trước
27 14
White
16 1
Giới thiệu Spring Framework Trong bài viết này, mình sẽ giới thiệu cho các bạn về một trong những Java EE framework rất nổi bật và phổ biến hiện n...
Nguyễn Tuấn Anh viết gần 3 năm trước
16 1
Bài viết liên quan
White
85 8
SOLID là gì – Áp dụng các nguyên lý SOLID để trở thành lập trình viên code “cứng” Trong quá trình học, hầu như các bạn sinh viên đều được học một s...
Huy Hoàng Phạm viết 4 năm trước
85 8
White
0 0
Clojure là ngôn ngữ functional có hỗ trợ OOP. Về mặt khoa học máy tính, có nhiều cách để thực hiện đa hình. Ở phiên bản trước 1.2, đa hình trong Cl...
Ngoc Dao viết hơn 3 năm trước
0 0
{{like_count}}

kipalog

{{ comment_count }}

bình luận

{{liked ? "Đã kipalog" : "Kipalog"}}


White
{{userFollowed ? 'Following' : 'Follow'}}
27 bài viết.
187 người follow

 Đầu mục bài viết

Vẫn còn nữa! x

Kipalog vẫn còn rất nhiều bài viết hay và chủ đề thú vị chờ bạn khám phá!