孙悟空战黄风怪
原始模型模式属于对象的创建模式[GOF95]。通过给出一个原型对象来指明所要创建的对象的类型,然后用复制这个原型对象的办法创建出更多同类型的对象。这就是原始模型模式的用意。
从孙大圣的手段谈起
---------------------
孙悟空在与黄风怪的战斗中,“使一个身外身的手段:把毫毛揪下一把,用口嚼得粉碎,望上一喷,叫声‘变!’变有百十个行者,都是一样打扮,各执一根铁棒,把那怪围在空中。” 换言之,孙悟空可以根据自己的形像,复制出很多“身外之身”来。
老孙的这种身外身的手段在面向对象的设计领域里,叫做原始模型(Prototype)模式。
Java语言的构件模型直接支持原始模型模式。所有的JavaBean都继承自java.lang.Object,而Object类提供一个clone()方法,可以将一个JavaBean对象复制一份;但是这个JavaBean必须实现一个标示接口Cloneable表明这个JavaBean支持复制。如果一个对象没有实现这个接口而调用clone()方法,Java编译器会抛出CloneNotSupportedException异常。(关于标示接口的概念及相关讨论,请见本书的“专题:Java接口”一章。)
Java的所有类都是从java.lang.Object类继承而来;而Object类提供下面的方法对对象进行复制:
protected Object clone()
子类当然也可以把这个方法置换掉,提供满足自己需要的复制方法。对象的复制有一个基本问题,就是对象通常都有对其它的对象的引用;当使用Object类的clone()方法来复制一个对象时,此对象对其它对象的引用也同时会被复制一份。
Java语言提供的Cloneable接口只起一个作用,就是在运行时期通知Java虚拟机可以安全地在这个类上使用clone()方法。通过调用这个clone()方法可以得到一个对象的复制。由于Object类本身并不实现Cloneable接口,因此如果所考虑的类没有实现Cloneable接口时,调用clone()方法会抛出CloneNotSupportedException异常。
系统可以在自己的类里面置换掉java.lang.Object提供的clone()方法,以便控制复制的过程。
克隆满足的条件
-------------
clone()方法将对象复制了一份并返还给调用者。所谓“复制”的含义与clone()方法是怎么实现的有关。一般而言,clone()方法满足以下的描述[BLOCH01]:
第一、对任何的对象x,都有:x.clone() != x;换言之,克隆对象与原对象不是同一个对象;
第二、对任何的对象x,都有:x.clone().getClass == x.getClass(),换言之,克隆对象与原对象的类型一样;
第三、如果对象x的equals()方法是定义恰当的话,那么 x.clone().equals(x)也应当是成立的。
在Java语言的API中,凡是提供了clone()方法的类,都满足上面的这些这些条件。Java语言的设计师在设计自己的clone()方法是,也应当遵守这三个条件。
一般来说,上面的三个条件中的头两个是必需的,而第三个是可选的;本书则推荐读者遵守所有的三个条件。
。。。下略。。。
阎宏博士,写于纽约
《Java与模式》作者
javapatterns@yahoo.com
http://www.WebEndsHere.com
http://www.yesky.com/20011108/203866.shtml
购书请到
http://www.china-pub.com/computers/common/info.asp?id=8182
http://www.huachu.com.cn/itbook/itbookinfo.asp?lbbh=BB07630282