首页 » 编写高质量代码:改善Java程序的151个建议 » 编写高质量代码:改善Java程序的151个建议全文在线阅读

《编写高质量代码:改善Java程序的151个建议》建议133:若非必要,不要克隆对象

关灯直达底部

通过clone方法生成一个对象时,就会不再执行构造函数了,只是在内存中进行数据块的拷贝,此方法看上去似乎应该比new方法的性能好很多,但是Java的缔造者们也认识到“二八原则”,80%(甚至更多)的对象是通过new关键字创建出来的,所以对new在生成对象(分配内存、初始化)时做了充分的性能优化,事实上,一般情况下new生成的对象比clone生成的性能方面要好很多,例如这样的代码。


private static class Apple implements Cloneable{

public Object clone(){

try{

return super.clone();

}catch(CloneNotSupportedException e){

throw new Error();

}

}}

public static void main(Stringargs){

//循环10万次

final int maxLoops=10*10000;

int loops=0;

//开始时间

long start=System.nanoTime();

//"母"对象

Apple apple=new Apple();

while(++loops<maxLoops){

apple.clone();

}

long mid=System.nanoTime();

System.out.println("clone方法生成对象耗时:"+(mid-start)+"ns");

//new生成对象

while(--loops>0){

new Apple();

}

long end=System.nanoTime();

System.out.println("new生成对象耗时:"+(end-mid)+"ns");

}


在上面的代码中,Apple是一个简单的可拷贝类,用两种方式生成了10万个苹果:一种是通过克隆技术,一种是通过直接种植(也就是new关键字),按照我们的常识想当然地会认为克隆肯定比new要快,但是结果却是这样的:


clone方法生成对象耗时:18731431 ns

new生成对象耗时:2391924 ns


不用看具体的数字,数数位数就可以了:clone方法花费的时间是8位数,而new方法是7位数,用new生成对象比clone方法快很多!原因是Apple的构造函数非常简单,而且JVM对new做了大量的性能优化,而clone方式只是一个冷僻的生成对象方式,并不是主流,它主要用于构造函数比较复杂,对象属性比较多,通过new关键字创建一个对象比较耗时间的时候。

注意 克隆对象并不比直接生成对象效率高。