工厂建设之路-- 简单工厂

Posted barneycs

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了工厂建设之路-- 简单工厂相关的知识,希望对你有一定的参考价值。

为什么要用工厂?

用工厂的主要目的是把对象的创建和使用分离,这比较符合单一职责原则,工厂负责创建产品,调用者负责使用产品,如果调用者既需要负责创建产品又需要负责使用产品,那么耦合性会比较高。
以一个常见的登录功能为例:

class HibernateUserDao {
    
    public void getUser() {
        System.out.println("Hibernate get user");
    }
}

public class UserService {
    private MybatisUserDao userDao;

    public UserService() {
        this.userDao = new MybatisUserDao();
    }

    public void login() {
        userDao.getUser();
    }
}

这样的坏处是什么呢?我们发现UserService的责任太重,不仅要创建UserDao的实例对象还要调用。假如现在公司为了统一项目都换成MyBatis那么更改起来非常麻烦。

简单工厂

我们对代码稍作修改:

/**
 * UserDao作为产品让工厂创建
 */
public interface UserDao {
    void getUser();
}

/**
 * UserDao的不同实现
 */
class MybatisUserDao implements UserDao {
    @Override
    public void getUser() {
        System.out.println("Mybatis get user");
    }
}

class HibernateUserDao implements UserDao {
    @Override
    public void getUser() {
        System.out.println("Hibernate get user");
    }
}

public class UserService {
    private UserDao userDao;

    public UserService(String name) {
        this.userDao = new MybatisUserDao();
    }

    public void login() {
        userDao.getUser();
    }
}

public class Factory {

    public static UserDao getUserDao(String name) {
        switch (name) {
            case "mybatis":
                return new MybatisUserDao();
            case "hibernate":
                return new HibernateUserDao();
            default:
                return null;
        }
    }
}
  1. 这样无论是创建MyBatis还是Hibernate的UserDao客户端都可以自由选择。
  2. 还有一个好处,UserDao这种对象往往不在一个地方被创建,如果用工厂统一管理起来,修改起来更方便,只需要修改一个Factory类就可以处处生效。
    但是这里有一个问题,我们发现简单工厂模式并不符合开闭原则,如果我们又需要增加UserDao的实现或者创建有所变动的话还是需要修改Factory类,并且客户端需要更改传入的值。在实际开发中可以通过配置文件替代传入的参数,这样可以避免修改客户端,而只需要配置不同的配置文件从而实现代码的复用。
    简单工厂并不是GOF23种设计模式之一,但是它是工厂方法和抽象工厂模式的基本形态,工厂方法和抽象工厂由它演变而来。

餐后甜点

我们来看一下JDK中的Integer的创建方式:

    public static Integer valueOf(int i) {
        if (i >= IntegerCache.low && i <= IntegerCache.high)
            return IntegerCache.cache[i + (-IntegerCache.low)];
        return new Integer(i);
    }

我们可以认为他把Integer的工厂和产品合并了,valueOf作为生产方法,这样做的好处是客户端使用这个方法可以用到IntegerCache的常量池优化,如果直接new就没有优化了。使用常量池也可以看做享元模式的思想,后面的博客会说到。




以上是关于工厂建设之路-- 简单工厂的主要内容,如果未能解决你的问题,请参考以下文章

测开之路十七:设计模式之简单工厂和工厂方法

智慧工厂协同管控应用系统软件建设方案

工程实践之路:C++接口设计中的工厂模型

[ZJOI2007]仓库建设

智慧工厂管理平台怎么建设,智慧工厂管理系统平台开发

智慧工厂管理平台建设,智慧工厂管理系统开发