原型模式。


创建型模式中还有一种与工厂方法模式完全不同的模式,就是原型模式。
 原型模式(Prototype Pattern)是创建型模式的一种,其特点在于通过“复制”一个已经存在的实例来返回新的实例,而不是新建实例。被复制的实例就是我们所称的“原型”,这个原型是可定制的。
  用面向对象的方法来说就是,我们先建立一个原型,然后通过对原型进行复制和修饰的方法,就可以产生一个与原型相似的新对象。即:用原型实例指定创建对象的种类,并且通过复制这些原型创建新的对象。
  在java中复制模型对象是通过clone()方法实现的。其实,这个方法可以是任意名字,比如cloneA(),cloneB()等。不过,一般应该使用clone()方法,这样做有两个原因:一是出于习惯,复制对象当然应该是clone();二是,在许多语言中的基础类中,比如做为所有类基础的Object,都定义了clone()方法。因此,实现原型模式的方法一般应该是原型类继承了Cloneable接口,在具体原型类中需要实现clone()方法,完成对象的自我复制。

  程序代码:

Java代码  

  1. public class Prototype implements Cloneable{  
  2.     
  3.   /** 
  4.   /*浅复制 
  5.   */  
  6.   public Object clone() throws CloneNotSupportedException{  
  7.   
  8.     Prototype prototype = (Prototype)super.clone();  
  9.     return prototype;  
  10.   }  
  11. }  



  调用Prototype模式很简单:
  Prototype obj = new Prototype();
  Prototype obj2 = obj.clone();//复制

  从以上的使用可以看出,在java中Prototype模式变成clone()方法的使用,此方法执行的是该对象的“浅复制”,而不是“深复制”操作。
  复制分为两种:浅复制和深复制
  ●浅复制:将一个对象复制之后,生成一个新的对象,新对象的所有成员变量(基本类型和引用类型)都含有与原来对象相同的值,如果原有对象的成员变量是基本数据类型,就会将这个变量的值复制一份到新对象里面,如果原有对象的成员变量是引用数据类型,那么这个引用指向的对象不会新生成一份,而是,在新对象里面的这个引用与原有对象的引用指向的是同一个对象。
  ●深复制:将一个对象复制之后,生成一个新的对象,新对象的基本数据变量含有与原有对象相同的值,如果原有对象的成员变量是引用数据类型,在新对象里面,这些引用变量将指向被复制过的新对象,而不再是指向原有的那些被引用的对象,深复制把要复制的对象所引用的对象都复制一遍。



    用原型实例制定创建对象的种类,并且通过拷贝这些原型创建新的对象。

    【原型模式UML图

    【原型模式-JAVA代码实现

    新建赛车的接口:


package car_interface;
public interface car_interface {
    
public void start();
    
public void stop();
}


    新建奥迪汽车的实现类:


package car_imple;
import car_fittings.car_tyre;
import car_interface.car_interface;
public class audi_imple implements car_interface, Cloneable {
    
private car_tyre car_tyre_ref;
    
public void start() {
        System.out.println(
"奥迪A6启动了");

    }

    
public void stop() {
        System.out.println(
"奥迪A6停止了");

    }

    
public car_tyre getCar_tyre_ref() {
        
return car_tyre_ref;
    }

    
public void setCar_tyre_ref(car_tyre car_tyre_ref) {
        
this.car_tyre_ref = car_tyre_ref;
    }

    @Override
    
public Object clone() throws CloneNotSupportedException {
        
super.clone();
        audi_imple audi_imple 
= new audi_imple();
        audi_imple.setCar_tyre_ref(
new car_tyre());

        
return audi_imple;
    }
}



  在奥迪汽车实现类中需要注意的是将原来protected类型的clone方法要变成public,这样才可以对外公开,可以被调用,将秘密公开化。

    新建奥迪汽车的配件轮胎类


package car_fittings;

public class car_tyre {

    
private String name = "德国制造原版轮胎";

    
public String getName() {
        
return name;
    }
}


    新建客户端运行类:


package run_main;

import car_fittings.car_tyre;
import car_imple.audi_imple;
import car_interface.car_interface;

public class run_main {

    
public static void main(String[] args) {

        
try {
            audi_imple car_ref_my 
= new audi_imple();
            car_ref_my.setCar_tyre_ref(
new car_tyre());
            System.out.println(
"我的奥迪车的参数是:" + car_ref_my);
            System.out.println(
"我的奥迪车的轮胎参数是:" + car_ref_my.getCar_tyre_ref());

            audi_imple car_ref_other 
= (audi_imple) car_ref_my.clone();
            System.out.println(
"其它人的奥迪车的参数是:" + car_ref_other);
            System.out.println(
"其它人的奥迪车的轮胎参数是:"
                    
+ car_ref_other.getCar_tyre_ref());

        } 
catch (CloneNotSupportedException e) {
            
// TODO Auto-generated catch block
            e.printStackTrace();
        }
    }
}


    程序运行结果如下:


我的奥迪车的参数是:car_imple.audi_imple@9cab16
我的奥迪车的轮胎参数是:car_fittings.car_tyre@1a46e30
其它人的奥迪车的参数是:car_imple.audi_imple@3e25a5
其它人的奥迪车的轮胎参数是:car_fittings.car_tyre@19821f


    从打印的结果来看,我的汽车我的轮胎和其它人的汽车和轮胎都是不一样的对象,但“类型”都是一样的:奥迪的汽车,原版的轮胎。本例中也实现了“原型模式”中的“深拷贝/深复制”,即汽车类中有一个对象“轮胎”对象,关于深拷贝/深复制的概念请参考其它的资料。原型模式通常都是在复制对象的时候使用,而在常规的情况下都是使用new重新创建一个,并且重新对属性进行复制,代码重复度很高,原型模式的出现避免了new的硬操作。

猜你喜欢

转载自rainyear.iteye.com/blog/1702875