初识设计模式

简单工厂模式

看完一些基础的讲解之后,我理解的工厂模式为:将代码里面的switch…case剥离出来,在其他地方对其进行实现;

对于输入的不同参数,会有不同的执行,如对以下的参数进行判断执行

1
2
3
4
5
6
public class AuditDTO {
Integer auditResult;
String auditContent;

public getter and setter;
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
public enum AuditResultEnum {
SUCCESS(1, "成功"),
FAIL(0, "失败");

private final Integer code;
private final String message;

public getter;

AuditResultEnum(Integer code, String message) {
this.message = message;
this.code = code;
}

public static AuditResultEnum getByCode(Integer code) {
for (AuditResultEnum _enum : values()) {
if (_enum.getCode().equals(code)) {
return _enum;
}
}
return null;
}
}

以面向过程的思维编写程序的话,如下:

1
2
3
4
5
6
7
8
9
10
switch (AuditResultEnum.getByCode(audit.getAuditResult())) {
case SUCCESS:
System.out.println(SUCCESS.getMessage());
break;
case FAIL:
System.out.println(FAIL.getMessage());
break;
default:
System.out.println("error");
}

对于这种最简单的switch这样写当然是没问题的,但是如果情况变得复杂,需要选择的条件变多之后,一旦某种情况需要修改,或是进行增加操作,直接在这段本就已经十分臃肿冗杂的代码里面进行修改,很有可能导致一些意想不到的问题;而且对于该段逻辑的修改需要编译整段代码,这样也是我们所不希望看见的。

那么如何使用工厂模式进行改进呢?

对于每一种case,将其置为一种实现,一般来说,每一种case我们都会处理相同的数据,如上文的auditResult,然后有不同的实现,因此我们需要一个抽象类,类中定义好我们所需要的数据&抽象方法

1
2
3
4
5
6
7
8
public abstract class Audit {
Integer auditResult;
String auditContent;

public getter and setter;

public abstract void audit();
}
1
2
3
4
5
6
7
8
9
10
public class AuditFail extends Audit {

@Override
public void audit() {
this.setAuditResult(AuditResultEnum.FAIL.getCode());
this.setAuditContent(AuditResultEnum.FAIL.getMessage());

System.out.println(this.toString());
}
}
1
2
3
4
5
6
7
8
9
10
public class AuditSuccess extends Audit {

@Override
public void audit() {
this.setAuditResult(AuditResultEnum.SUCCESS.getCode());
this.setAuditContent(AuditResultEnum.SUCCESS.getMessage());

System.out.println(this.toString());
}
}

然后将代码中的switch语句提取出来,进行判断何时使用何类

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
public class AuditFactory
{
public void audit(AuditDTO audit) {
switch (AuditResultEnum.getByCode(audit.getAuditResult())) {
case SUCCESS:
AuditSuccess auditSuccess = new AuditSuccess();
auditSuccess.setAuditResult(audit.getAuditResult());
auditSuccess.setAuditContent(audit.getAuditContent());
auditSuccess.audit();
break;
case FAIL:
AuditFail auditFail = new AuditFail();
auditFail.setAuditResult(audit.getAuditResult());
auditFail.setAuditContent(audit.getAuditContent());
auditFail.audit();
break;
default:
System.out.println("error");
}
}
}

然后我们在业务中,只需要简单地调用该工厂函数即可,以后对于某种case的修改只需要到该情况的case类中进行修改,而不必在业务实现的代码中修改,避免出错。

1
2
3
4
5
6
7
8
9
10
public class FactoryPatternTest {
public static void main(String[] args) {
AuditDTO auditFailure = new AuditDTO(0, "我觉得可以失败");
AuditDTO auditSuccess = new AuditDTO(1,"我觉得可以成功");

AuditFactory auditFactory = new AuditFactory();
auditFactory.audit(auditFailure);
auditFactory.audit(auditSuccess);
}
}