欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

设计模式学习笔记——原型模式

程序员文章站 2022-06-12 22:30:09
...

 

原型模式

利用原型模式,可以指定程序中所需的一般类,但是具体类的指定则推迟到执行期间去完成。

看上去很拗口,更多地方队原型模式的定义是:

通过给出一个原型对象来指明所要创建的对象的类型,然后用复制这个原型对象的办法创建出更多同类型的对象。

简单的说,就是通过复制,然后适当的修改,来创建一个新的对象。

 

Java中因为有clone(),所以原型模式的实现非常简单

对于clone()来说,有几点:

1 它是一个保护方法,只能在同一个类或者子类内调用

2 只能复制那些声明为实现了Cloneable接口的对象。所有数组对象都默认实现了Cloneable接口

3 类为Object的任何对象没有实现Cloneable,会抛出CloneNotSupported的异常

综上 我们要把公用,可见的clone方法打包在类中,从而使之可以被访问。

由于clone方法返回的是一个Object对象,因此必须将它强制转换成要复制的对象类型

 

原型模式的基本实现就是基于clone()

首先,它有一个抽象类,给出了所有具体类所需要的接口等

 

public class AbstractProduct implements Cloneable{

        .....

	public Object clone() throws CloneNotSupportedException{  
        return super.clone();  
    }
}

 

然后是一个具体的原型,是对抽象类的实现,也是被clone的对象

public class ConcreteProduct extends AbstractProduct{
	......
}

最后,我们来构建我们需要的对象

 

public class Client {
	public static void main(String[] args) throws CloneNotSupportedException {
		AbstractProduct product=new ConcreteProduct();
		AbstractProduct cloneProduct=(AbstractProduct)product.clone();
	}
}

 使用原型模式的一些结论

 

在运行时,可以根据需要,以复制的方式增加和删除类

可以基于程序条件,在运行时修改一个类的内部数据表示

还可以在运行时指定新的对象,而无需创建一系列类和继承结构

拷贝原型类的思想以为着可以充分访问这些类中的数据或方法,从而在复制之后将其加以修改。这可能要求向某些原型类增加数据访问方法,一遍复制了类后可以修改数据。

 

 

讨论完基础的原型模式,还有一些必要的补充(这里的概念copy了某日志 我在最后贴了链接 希望原作者不要介意)

首先,是对于clone方法,clone方法在Java中实现的浅拷贝

被复制对象的所有变量都含有与原来的对象相同的值,而所有的对其他对象的引用都仍然指向原来的对象,换言之, 浅复制仅仅复制所考虑的对象,而不复制它所引用的对象。

深拷贝

被复制对象的所有的变量都含有与原来的对象相同的值,除去那些引用其他对象的变量。那些引用其他对象的变量将 指向被复制过的新对象,而不再是原有的那些被引用的对象。换言之,深复制把要复制的对象所引用的对象都复制了 一遍,而这种对被引用到的对象的复制叫做间接复制。 

 

要实现深拷贝,就提到了串行化,有一种技巧,称作“hack(出租)”。

把一个类写作为一个字节流,并且将那些字节再读回来重新构造该类,就是串行化。这里要使用到Serializable接口,同Cloneable类似,他们不含任何方法,只是一个标示声明。

public class deepClone{
	public Object deepClone() throws IOException, ClassNotFoundException{ 
	//将对象写到流里 
	ByteArrayOutputStream bo = new ByteArrayOutputStream(); 
	ObjectOutputStream oo = new ObjectOutputStream(bo); 
	oo.writeObject(this); 
	//从流里读回来 
	ByteArrayInputStream bi = new ByteArrayInputStream(bo.toByteArray()); 
	ObjectInputStream oi = new ObjectInputStream(bi); 
	return (oi.readObject()); 
	}
}

 最后,原型模式同单例模式一样,也有注册表管理式的,实现的原理相似,构造一张表,在复制时进行查找。

 

关于原型模式,有一些内容来自

http://www.iteye.com/topic/503040

还有一个关于创建型设计模式的博客

http://icyfenix.iteye.com/blog/575049

对星际争霸熟悉的 看起来会很有思路 非常不错

 

另外 关于Java中clone的问题

http://www.iteye.com/topic/483469

给出了一定的研究 可以看看

 

到此为止 所有的创建型设计模式笔记结束了,一些tips来的小结

工厂模式:根据提供给该工厂的数据,选择并返回多个相似类中某个类的一个实例

抽象工厂模式:返回多组类中的一组。在有些情况下,它实际上返回的是该组类的一个工厂模式

生成器模式:根据所提供的数据,将多个对象组合以得到一个新的对象。通常使用一个工厂模式选择组合对象的方式

原型模式:当创建新的实例代价更大时,可采用拷贝或者复制一个现有类的方法,而不是创建一个新的实例。

单例模式:确保一个对象有且只有一个实例,并且可以获取该实例的一个全局访问点