1,抽象工厂模式
提供给客户端一系列与需求相关的,相互依赖的接口,通过接口的调用的可变性来提高代码的适用性。举个例子,在开发中,我们使用不同的数据库的语法不一样,Oracle与Mysql例如分页上语法不一,MongoDB操作为指令性操作,后台通过getCommand()方法来操作MongoDB,因为需求的对数据库类型的改变就需要修改很多代码,通过抽象工厂模式可以起到灵活转换,代码使用性提高的作用。下面的代码省略了MongoDB实现User接口与创建MongoDB工厂的类。
public interface User {
public void getUser();
public void setUser();
}
public class SqlServerUse implements User {
@Override
public void getUser() {
System.out.println("SqlServer获取User");
}
@Override
public void setUser() {
System.out.println("SqlServer插入User");
}
}
public interface IFctory {
public User createUser();
}
public class SqlServerFactory implements IFctory{
@Override
public User createUser() {
return new SqlServerUse();
}
}
抽象工厂模式的缺点:
看一下抽象工厂模式的架构图,虽然做到了设计模式中单一职责原则,对每个的类的修改变少了,但是抽象工厂模式只对既定的转换情况表现灵活性,对于需求转换的大更改,就会要求增加很多的类,使用起来并不方便。
用反射改进抽象工厂模式:
去掉抽象工厂模式中的IFactory与每个数据库具体实现返回实例的Factory类。用反射来实例化对象。这样对于需求的更改,只需要增加对实体类需要的数据库操作类就可以了,即上面的实现User的类。在设计中应该更多的减少原有代码上的更改,这里的代码可以通过Spring框架依赖注入的原理,在xml文件中配置databaseName,然后让ReflectFactoryUse去解析Xml拿到databaseName。
public class ReflectFactoryUse {
private static String databaseName = "SqlServer";
public User getUseFactory() throws InstantiationException, IllegalAccessException{
String clazzName = "com.fyihan.abstractFactoryModel."+databaseName+"Use";
Class clazz = null;
try {
clazz= Class.forName(clazzName);
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
return (User)clazz.newInstance();
}
}
2,状态模式
当一个对象内部的状态发生了改变,同时行为也跟着发生改变。常规的操作会通过if...else if......else if...../switch ... case x:.....来对状态发的改变判断然后做出行为改变。状态模式,用于简化语句判断的冗长,让对象中状态发生改变时,行为改变就像改变了这个类。在具体的对象中,构造初始化最早发生的状态,然后通过对每个状态的封装来解决冗长问题,也方便日后需求修改,对于状态添加或者修改的需求。
abstract class State {
abstract void handle(UsallyLife ul);
}
class TorrowLife extends State {
@Override
void handle(UsallyLife ul) {
if(ul.hour == 9.00){
System.out.println("现在是9点,状态:9点");
}else{
MoringLife ml = new MoringLife();
ml.handle(ul);
}
}
}
class MoringLife extends State {
@Override
void handle(UsallyLife ul) {
if(ul.hour==9.30){
System.out.println("现在是9.30,是工作时间了,写代码");
}else{
LunchLife ll = new LunchLife();
ll.handle(ul);
}
}
}
class LunchLife extends State {
@Override
void handle(UsallyLife ul) {
if(ul.hour==12.00){
System.out.println("现在是12.00午餐时间");
}else{
AfterLife al = new AfterLife();
al.handle(ul);
}
}
}
class AfterLife extends State {
@Override
void handle(UsallyLife ul) {
if(ul.hour==12.30){
System.out.println("现在是下午时间12.30,开始学习,写代码");
}
}
}
class UsallyLife {
double hour;
private State state;
UsallyLife(){
this.state = new TorrowLife();
}
void writeUrl(UsallyLife ul){
this.state.handle(ul);
}
}
class Main {
static void main(String[] args) {
UsallyLife ul = new UsallyLife();
ul.hour =9.00;
ul.writeUrl(ul);
ul.hour =9.30;
ul.writeUrl(ul);
ul.hour = 12.00;
ul.writeUrl(ul);
ul.hour =12.30;
ul.writeUrl(ul);
}
}