设计原则
约 615 字大约 2 分钟
设计模式设计原则
2026-04-14
SOLID 原则
| 原则 | 全称 | 描述 |
|---|---|---|
| SRP | 单一职责原则 | 一个类应该只有一个引起它变化的原因 |
| OCP | 开闭原则 | 软件实体应该对扩展开放,对修改封闭 |
| LSP | 里氏替换原则 | 子类必须能够替换其父类 |
| ISP | 接口隔离原则 | 不应该强迫客户依赖于它们不用的方法 |
| DIP | 依赖倒置原则 | 高层模块不应该依赖低层模块,两者都应该依赖抽象 |
单一职责原则 (SRP)
// 违反 SRP:一个类负责多项职责
class User {
constructor(public name: string, public email: string) {}
validate() {} // 验证职责
save() {} // 存储职责
sendEmail() {} // 通知职责
}
// 符合 SRP:每个类只负责一项职责
class UserValidator { validate() {} }
class UserRepository { save() {} }
class EmailService { sendEmail() {} }开闭原则 (OCP)
// 违反 OCP:修改现有代码来添加新功能
class AreaCalculator {
calculate(shape: string, data: number[]) {
if (shape === 'circle') {
return Math.PI * data[0] ** 2;
}
if (shape === 'square') {
return data[0] * data[1];
}
}
}
// 符合 OCP:对扩展开放
abstract class Shape {
abstract area(): number;
}
class Circle extends Shape {
constructor(public radius: number) { super(); }
area() { return Math.PI * this.radius ** 2; }
}
class Square extends Shape {
constructor(public side: number) { super(); }
area() { return this.side ** 2; }
}里氏替换原则 (LSP)
子类必须能够替换其父类,而不破坏程序的正确性。
// 违反 LSP:子类改变了父类的行为契约
class Rectangle {
constructor(public width: number, public height: number) {}
setWidth(w: number) { this.width = w; }
setHeight(h: number) { this.height = h; }
}
class Square extends Rectangle {
setWidth(w: number) {
this.width = w;
this.height = w; // 改变了行为
}
}
// 符合 LSP:保持行为一致依赖倒置原则 (DIP)
// 违反 DIP:高层模块依赖低层模块
class MySQL {
connect() {}
}
class UserService {
private db = new MySQL(); // 直接依赖具体实现
}
// 符合 DIP:依赖抽象
interface Database {
connect(): void;
}
class UserService {
constructor(private db: Database) {} // 依赖抽象
}其他原则
迪米特法则
一个对象应该对其他对象有最少的了解。只与直接的朋友通信。
// 违反迪米特法则
class Teacher {
remove(student: Student) {
// Teacher 直接操作 StudentGroup 的内部
const group = student.group;
group.remove(student);
}
}
// 符合迪米特法则
class Teacher {
removeFromGroup(student: Student) {
student.removeFromGroup();
}
}合成复用原则
优先使用组合而不是继承。
// 违反合成复用原则:使用继承
class Dog extends Animal {
swim() {} // 不是所有 Dog 都会游泳
}
// 符合合成复用原则:使用组合
class Dog implements Swimmer {
swim() { /* ... */ }
}
interface Swimmer {
swim(): void;
}