`
airu
  • 浏览: 267498 次
  • 性别: Icon_minigender_1
  • 来自: 云南
社区版块
存档分类
最新评论

每天一个(设计模式)--工厂模式与抽象工厂模式

 
阅读更多
工厂模式,属于创建型模式,我们不在自己创建对象,而是交由工厂来创建。
这样的好处是,我们使用工厂来封装对对象的需求,否则,你可能写一大堆if else来判断,然后新增一个对象的话,又得改这段代码。

简单的工厂模式就是,调用者对工厂说,给我一个A零件,工厂就创建一个A零件,调用者说,给我一个C零件,工厂就创建一个C零件。就这么简单。

上图(借用别人的,学习目的:)):




这种简单的代码更清晰:
#产品接口
public interface Product {
	public String getName();
}
#产品A
public class ProductA implements Product{

	@Override
	public String getName() {
		// TODO Auto-generated method stub
		return "A";
	}

}
#产品B
public class ProductB implements Product {

	@Override
	public String getName() {
		// TODO Auto-generated method stub
		return "B";
	}

}
#工厂
public class ProductFactory {
	public static Product getProduct(String name){
		if("A".equals(name)){
			return new ProductA();
		}else if("B".equals(name)){
			return new ProductB();
		}else return null;
	}
}



其实简单工厂模式看上不这么的。还是很废话。如果新增产品C,D,E呢?
一样需要修改工厂。这时用户使用的工厂还是需要改动。这里我们可以用很多方法,例如使用反射,或者使用动态注册(工厂能生产的产品都要在工厂中注册,使用一个key/value来实现,key为名称,value就是创建对象的具体方法或实例)

这时,问题还没有完,工厂的能力是无限的,这时工厂需要生产与上面的产品参数不一样的产品了,这怎么办? 其实上面的工厂是一个很不好的例子,因为这样我们又得增加if else语句了。这下我们发现,其实工厂也是会改变的。那么就把改变的东西封装起来吧。
于是出现了抽象工厂。我们的抽象工厂与抽象产品做接口,具体的东西,就由下面的实现类去折腾吧。


这里,我们把上面的例子改改,假设产品A与产品B不是同一类产品了,他们的创建方法不一样了,A需要增加一个序列号。

public class ProductA implements Product{

	private long sero ;
	@Override
	public String getName() {
		// TODO Auto-generated method stub
		return "A";
	}
	
	public void setSero(long sero){
		this.sero = sero;
	}

}



而此时,我们的工厂也变成抽象的了。
public interface AbstractFactory {
	public  Product getProduct();
}
#factory a create productA
public class FactoryA implements AbstractFactory {
	
	private static FactoryA _instance;
	private FactoryA(){}
	public static FactoryA getInstance(){
		if(_instance==null){
			_instance = new FactoryA();
		}
		return _instance;
	}

	@Override
	public  Product getProduct() {
		// TODO Auto-generated method stub
		ProductA p = new ProductA();
		p.setSero(10000L);
		return p;
	}
}
//factory B create ProductB类似,略去
//使用
	public static void main(String[] args) {
		// TODO Auto-generated method stub
		Product p = FactoryA.getInstance().getProduct();
		System.out.println(p.getName());
	}


这里对工厂使用了单例模式。怎么样,抽象工厂代码更为简洁吧,实际中,可能会拥有很多的产品与工厂,这就需要权衡抽象工厂和简单工厂了。
总之,设计模式中,粒度问题是一个关键问题,如何衡量系统的类的粒度,和系统自身息息相关。如果能准确把握,就能很优雅的解决问题。

  • 大小: 4.2 KB
  • 大小: 2.9 KB
分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics