单一职责(Simple Responsibility Pinciple,SRP)是指不要存在多于一个导致类变更的原因。假设我们有一个类负责两个职责,一旦需求发生变更,修改其中一个职责的业务逻辑代码时,有可能导致另一个职责的功能发生故障。这样一来,这个类就存在两个导致类变更的原因。
如何去解决这个问题呢?很简单,将两个职责用两个类来实现,进行解耦。后期需求变更和维护互不影响。这样的设计,可以降低类的复杂度,提高类的可读性,提高系统的可维护性,降低代码变更引起的风险。
总而言之,就是尽可能的让一个类,接口或者方法只负责一项职责。
来看一段代码帮助理解,还是拿书举例。现在这些书,成了电子书。电子书分免费书和付费书。免费书可以任意观看,付费书仅限VIP观看,功能职责不一样。先创建一个Book类:
/**
* @Author: zhouzhen
* @email: zhouzhen0517@foxmail.com
* @Description
* @Date: Create in 12:39 2020/4/9
*/
public class Book {
public void read(String bookName) {
if("免费书".equals(bookName)) {
System.out.println("可以任意观看");
} else {
System.out.println("仅限VIP观看");
}
}
}
来看一下调用代码
public static void main(String[] args) {
Book book = new Book();
book.read("免费书");
book.read("付费书");
}
从上面的代码看,Book类承担了两种处理逻辑。假如现在要对电子书进行加密,免费书和付费书的加密逻辑不一样,必须修改代码。而修改代码势必会相互影响,容易带来不可控的风险。现在我们来对职责进行解耦,来看代码,分别创建两个类:FreeBook和PayBook。
FreeBook的代码如下:
/**
* @Author: zhouzhen
* @email: zhouzhen0517@foxmail.com
* @Description
* @Date: Create in 13:41 2020/4/10
*/
public class FreeBook {
public void read(String bookName) {
System.out.println(bookName + "可以任意观看");
}
}
PayBook的代码如下:
/**
* @Author: zhouzhen
* @email: zhouzhen0517@foxmail.com
* @Description
* @Date: Create in 13:41 2020/4/10
*/
public class PayBook {
public void read(String bookName) {
System.out.println(bookName + "仅限VIP观看");
}
}
调用代码如下:
public static void main(String[] args) {
FreeBook freeBook = new FreeBook();
PayBook payBook = new PayBook();
freeBook.read("免费书");
payBook.read("付费书");
}
修改之后,各个类负责各自的职责,开发起来简单,维护起来也容易。我们在实际开发中会有项目依赖,组合,聚合这些关系,还有项目的规模,周期,技术人员的水平,对进度的把控。出于各方面的妥协,很多类的设计都不符合单一职责原则。但是,我们在编写代码的过程中,还是要尽可能的让接口和方法保持单一职责,对项目的后期维护是有很大帮助的。
文章参考
《Spring5核心原理》〔中〕谭勇德(Tom)