关闭

第五 避免不必要的对象

标签: java
81人阅读 评论(0) 收藏 举报
分类:

java 中流行一句话:万物皆对象

对象,能复用的最好不要重新创建,重用即快速又流行。如果对象不可变,它始终可以被复用。列举一个极端的反例,字符串

String s = new String("hello");

这里面有两个实例对象,一个是字符串“hello” 本身,一个是 s 。平白无故的多创建了一个对象,改进后版本为 String s = “hello”;即可

这个版本用了一个String 实例。并且对于同一台虚拟机中,相同的字符串字面常量,该对象就会被重用。

例如 

public static Boolean valueOf(boolean b) {

        return (b ? TRUE : FALSE);

    }

public static Boolean valueOf(String str) {

        return ("true".equals(str) ? TRUE : FALSE);

    }

中,Boolean.valueOf(String) 总是优先于构造器 Boolean(String) 


避免创建多余对象是规则,也是用于静态方法中,比如

计算时间经常会用到 Calendar 这个工具类,通常做法是在方法里面创建,每调用一次,创建一次

public static boolean isBorth(String day){

Calendar  cal = Calendar.getInstance();

int start = cal.getTime();

....

}

这样cal被不停的创建,可初步优化,把cal设置为成员变量,做非空判断

static Calendar  cal;

public static boolean isBorth(String day){

if(cal == null){

cal = Calendar.getInstance();

}

int start = cal.getTime();

....

}


这样做避免了cal被多次初始化,但存在两个小问题,一个是高并发,不能保证只创建了一个,就像是单例模式的懒汉式,另外一个就是每次调用都做了一次非空判断,初次时很有必要,创建对象,创建对象成功后,为了避免重新创建,需要判断,但我们能不能想办法去掉判断呢? 能 !用第一篇所说的static

可以用static代码块来改进

static Calendar  cal;

static{

cal = Calendar.getInstance();

}

public static boolean isBorth(String day){

int start = cal.getTime();

....

}

这样在大量调用该方法时,效率会有显著提高。


java jdk 1.5 以后有个自动装箱的概念,这样基本类型和装箱类型可以混用。但装箱类型都是对象,存在一个地址值。使用不恰当的话,很容易消耗不必要的内存

看个例子,

 public static void main(String[] args) {
Long num = 0L;
for(int x = 0; x<Integer.MAX_VALUE; x++){
num+=x;
}
System.out.println(num);
这段代码结果正确,但耗时。因为num的声明时Long而不是long,由于自动装箱的原因,这个方法多出了2的31次方个实例对象,
这个时joshua大神举的例子,在机器上运行时间为40多秒,改为long后,时间大概为6秒,由此可见一个小细节产生的问题。

创建对象代价并不昂贵,现在的jvm优化的很好,很容易回收无用的对象。但在优化代码,提高代码质量上,在有把握的前提下,尽量对象复用。

0
0

查看评论
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
    个人资料
    • 访问:5856次
    • 积分:482
    • 等级:
    • 排名:千里之外
    • 原创:45篇
    • 转载:0篇
    • 译文:0篇
    • 评论:0条
    文章分类