Effective java第一条:考虑用静态工厂方法代替构造器

一、创建对象

构造方法
public Boolean(String s) {
  this(toBoolean(s));
}
Boolean bTrue = new Boolean("true");
静态工厂方法
public static Boolean valueOf(String s) {
  return toBoolean(s) ? TRUE : FALSE;
}
Boolean bTrue = Boolean.valueOf("true");

二、使用静态工厂方法的优点

1、它们有名称
2、它们可以返回原返回类型任意子类型的对象。

  针对于第一点,相比较于与类名相同的构造函数,静态工厂方法是通过静态方法进行对象的初始化,其方法名字自然可以自定义,从而帮助开发人员的理解,这是容易理解的。例如,重载而来的构造函数,很难在不看源码的情况下知道他们的区别。
  第二点,其在Java中的集合类Collections用的颇多,主要利用Java的多态的特性,使得工厂可以产生基类的同时注入子类实现。

public interface Food {

    /**
     * 使得所有食物都有一个共有的introduce方法
     */
    public void introduce();
}

/**
 * 定义食物的子类:鱼
 */
public class Fish implements Food{

    @Override
    public void introduce() {
        System.out.println("i am a fish");
    }
}

/**
 * 食物的子类,水果
 */
public class Fruit implements Food {
    @Override
    public void introduce() {
        System.out.println("i am the fruit");
    }
}

/**
 * 通过反射机制实现的工厂
 */
public class FoodFactory {

    public static Food getFood(String type) {
        Food food = null;
        try {
            food = (Food) Class.forName("info.zhw." + type).newInstance();
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        } catch (InstantiationException e) {
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            e.printStackTrace();
        }
        return food;
    }
}

 
  FoodFactory就利用了基类,返回了该类型的子类型。

3、不必在每次调用他们的时候都创建一次对象。

  使用构造函数,调用其中的方法,则实例化一个类是必不可少的步奏,而是使用静态工厂方法,则可以对对象进行重复利用,这个特点在单例模式中使用颇多。

public class SingletonClass{
    private static SingletonClass instance=null;
    public static SingletonClass getInstance()
    {
        if(instance==null)
        {
            synchronized(SingletonClass.class)
            {
                if(instance==null)
                    instance=new SingletonClass();
            }
        }
        return instance;
    }
    private SingletonClass(){
    }
}

其将构造方法私有,只能通过getInstance()获取实例,从而达到实例重复利用的目的。

4、使代码简洁

三、使用静态工厂方法的缺点

1、如果类不含有公有或受保护构造器,就不能被子类化。
2、和静态方法实际上没有任何区别。

  其无法在API文档中明确标出,推荐使用管用名称管理。

3、

  由于工厂类集中了所有实例的创建逻辑,这就直接导致一旦这个工厂出了问题,所有的客户端都会受到牵连;而且由于简单工厂模式的产品室基于一个共同的抽象类或者接口,这样一来,但产品的种类增加的时候,即有不同的产品接口或者抽象类的时候,工厂类就需要判断何时创建何种种类的产品,这就和创建何种种类产品的产品相互混淆在了一起,违背了单一职责,导致系统丧失灵活性和可维护性。而且更重要的是,简单工厂模式违背了“开放封闭原则”,就是违背了“系统对扩展开放,对修改关闭”的原则,因为当我新增加一个产品的时候必须修改工厂类,相应的工厂类就需要重新编译一遍。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值