Nguyên lý thay thế Liskov - Liskov substitution principle

Nguyên lý thay thế Liskov (Liskov substitution principle - LSP) là một nguyên lý cơ bản trong thiết kế phần mềm hướng đối tượng. Nó là nguyên lý thứ ba trong bộ nguyên lý SOLID


Nguyên lý này hơi trừu tượng và khó hiểu
Trong một chương trình, các class con phải thay thế được class cha mà không làm thay đổi tính đúng đắn của chương trình

Ví dụ minh họa
Ví dụ thứ nhất, class con quăng exception khi gọi hàm
Giả sử, ta muốn viết một chương trình để mô tả các loài chim bay. Đại bàng, chim sẻ, vịt bay được, nhưng chim cánh cụt không bay được. Do chim cánh cụt cũng là chim, ta cho nó kế thừa class Bird. Tuy nhiên, vì cánh cụt không biết bay, khi gọi hàm bay của chim cánh cụt, ta sẽ quăng NoFlyException.


Ta tạo 1 mảng chứa các loài chim rồi duyệt các phần tử. Khi gọi hàm Fly của class Penguin, hàm này sẽ quăng lỗi. Class Penguin gây lỗi khi chạy, không thay thế được class cha của nó là Bird, do đó nó đã vi phạm LSP.

Ví dụ thứ hai, class con thay đổi hành vi class cha


Đây là ví dụ kinh điển về hình vuông và hình chữ nhật mà mọi người thường dùng để giải thích LSP
Ta có 2 class cho hình vuông và hình chữ nhật. Ai cũng biết hình vuông là hình chữ nhật có 2 cạnh bằng nhau, do đó ta có thể cho class Square kế thừa class Rectangle để tái sử dụng code.
Do hình vuông có 2 cạnh bằng nhau, mỗi khi set độ dài 1 cạnh thì ta set luôn độ dài của cạnh còn lại. Tuy nhiên, khi chạy thử, hành động này đã thay đổi hành vi của của class Rectangle, dẫn đến vi phạm LSP.

Trong trường hợp này, để code không vi phạm LSP, ta phải tạo 1 class cha là class Shape, sau đó cho Square và Rectangle kế thừa class Shape này.


Kết luận
Đây là nguyên lý dễ bị vi phạm nhất, nguyên nhân chủ yếu là do sự thiếu kinh nghiệm khi thiết kế class. Thông thường, design các class dựa theo đời thật: hình vuông là hình chữ nhật, chim cánh cụt là chim. Tuy nhiên, không thể bê nguyên văn mối quan hệ này vào code


Tiếp tục cập nhật ...