原型(Prototype)模式的Java实现[00原创]

来源:互联网 发布:mac word 文件恢复 编辑:程序博客网 时间:2024/04/27 18:56
在Java里,这个模式主要与clone()方法密切相关。

1. 类图

 

2. Java实现代码

package cn.edu.ynu.sei.prototype;

/**
 * 原始模型模式客户端
 * 
 * 
@author 88250
 * 
@version 1.0.0, 2007-8-26
 
*/
public class Client
{
    
private Prototype prototype;
 
    
/**
     * 
     * 
@param example
     
*/
    
public void operation(Prototype example)
    {
    Prototype p 
= (Prototype) example.clone();
    }
}
package cn.edu.ynu.sei.prototype;

/**
 * 具体原型类,使用{
@link #clone()}方法进行浅克隆
 * 
 * 
@author 88250
 * 
@version 1.0.0, 2007-8-26
 
*/
public class ConcretePrototype implements Prototype
{
    
/**
     * 克隆方法
     * 
     * 
@return
     
*/
    @Override
    
public Object clone()
    {
    
try
    {
        
return super.clone();
    }
    
catch (CloneNotSupportedException cnse)
    {
        
return null;
    }
    }
}
package cn.edu.ynu.sei.prototype;

/**
 * 原型接口<br>
 * 继承于<code>java.lang.Cloneable</cdoe>接口,标识本接口可以使用
 * {
@link #clone()}方法
 * 
@author 88250
 * 
@version 1.0.0, 2007-8-26
 
*/
public interface Prototype extends Cloneable
{
    
public Object clone();
}

3. 总结

在Java里,原型模式主要就是使用clone()方法去实现,但是要注意的是clone()方法是浅克隆(shallow clone)的。细节部分可以参考clone()的JavaDoc注释。里面说明了clone()方法满足的条件:
Object java.lang.Object.clone() throws CloneNotSupportedException

Creates and returns a copy of this object. The precise meaning of "copy" may depend on the class of the object. The general intent is that, for any object x, the expression:

 x.clone() != x
will be true, and that the expression:
 x.clone().getClass() == x.getClass()
will be true, but these are not absolute requirements. While it is typically the case that:
 x.clone().equals(x)
will be true, this is not an absolute requirement.

By convention, the returned object should be obtained by calling super.clone. If a class and all of its superclasses (except Object) obey this convention, it will be the case that x.clone().getClass() == x.getClass().

By convention, the object returned by this method should be independent of this object (which is being cloned). To achieve this independence, it may be necessary to modify one or more fields of the object returned by super.clone before returning it. Typically, this means copying any mutable objects that comprise the internal "deep structure" of the object being cloned and replacing the references to these objects with references to the copies. If a class contains only primitive fields or references to immutable objects, then it is usually the case that no fields in the object returned by super.clone need to be modified.

The method clone for class Object performs a specific cloning operation. First, if the class of this object does not implement the interface Cloneable, then a CloneNotSupportedException is thrown. Note that all arrays are considered to implement the interface Cloneable. Otherwise, this method creates a new instance of the class of this object and initializes all its fields with exactly the contents of the corresponding fields of this object, as if by assignment; the contents of the fields are not themselves cloned. Thus, this method performs a "shallow copy" of this object, not a "deep copy" operation.

The class Object does not itself implement the interface Cloneable, so calling the clone method on an object whose class is Object will result in throwing an exception at run time.

下面,我们来看看什么是深克隆和浅克隆的不同。
简单地说,深克隆就是对该对象所引由的所有对象都进行克隆。比如,一个对象有一个属性为类类型,这个时候如果使用的是浅克隆,那么就只是将这个属性字段的实例引用复制给了克隆对象的属性字段,所以源对象和拷贝对象的这个字段都是引用了同一个实例。而深克隆则是对这个字段也进行复制,而不是只更改引用。这里就有一个问题,如果这个字段也存在一个属性是类类型怎么办呢?
要解决这个问题就看你的应用程序的需要了,因为在Java里使用深拷贝都是将一个类实现Serializable接口,使用Java的“冷藏”和“解冻”方法去进行深克隆,所以,程序员完全可以根据应用的需要而设计深克隆层次深度。
最后,在罗嗦一下,关于克隆与“冷藏”和“解冻”方法,这里有个我写的示例代码可以参考 :-)

4. 参考文献

  《Design Patterns》、《Java与模式》
原创粉丝点击