A股上市公司传智教育(股票代码 003032)旗下技术交流社区北京昌平校区

© mimawo 中级黑马   /  2016-4-30 20:56  /  314 人查看  /  0 人回复  /   0 人收藏 转载请遵从CC协议 禁止商业使用本文

四、反射性能:
反射是一种强大的工具,但也存在一些不足。一个主要的缺点是对性能有影响。使用反射基本上是一种解释操作,我们可以告诉JVM,我们希望做什么并且它满足我们的要求。这类操作总是慢于只直接执行相同的操作。


下面的程序是字段接入性能测试的一个例子,包括基本的测试方法。每种方法测试字段接入的一种形式 -- accessSame 与同一对象的成员字段协作,accessOther 使用可直接接入的另一对象的字段,accessReflection 使用可通过反射接入的另一对象的字段。在每种情况下,方法执行相同的计算 -- 循环中简单的加/乘顺序。


程序如下:


public int accessSame(int loops) {


    m_value = 0;


    for (int index = 0; index < loops; index++) {


        m_value = (m_value + ADDITIVE_VALUE) *


            MULTIPLIER_VALUE;


    }


    return m_value;


}


public int accessReference(int loops) {


    TimingClass timing = new TimingClass();


    for (int index = 0; index < loops; index++) {


        timing.m_value = (timing.m_value + ADDITIVE_VALUE) *


            MULTIPLIER_VALUE;


    }


    return timing.m_value;


}


public int accessReflection(int loops) throws Exception {


    TimingClass timing = new TimingClass();


    try {


        Field field = TimingClass.class.


            getDeclaredField("m_value");


        for (int index = 0; index < loops; index++) {


            int value = (field.getInt(timing) +


                ADDITIVE_VALUE) * MULTIPLIER_VALUE;


            field.setInt(timing, value);


        }


        return timing.m_value;


    } catch (Exception ex) {


        System.out.println("Error using reflection");


        throw ex;


    }


}


在上面的例子中,测试程序重复调用每种方法,使用一个大循环数,从而平均多次调用的时间衡量结果。平均值中不包括每种方法第一次调用的时间,因此初始化时间不是结果中的一个因素。下面的图清楚的向我们展示了每种方法字段接入的时间:

字段接入时间 :


我们可以看出:在前两副图中(Sun JVM),使用反射的执行时间超过使用直接接入的1000倍以上。通过比较,IBM JVM可能稍好一些,但反射方法仍旧需要比其它方法长700倍以上的时间。任何JVM上其它两种方法之间时间方面无任何显著差异,但IBM JVM几乎比Sun JVM快一倍。最有可能的是这种差异反映了Sun Hot Spot JVM的专业优化,它在简单基准方面表现得很糟糕。反射性能是Sun开发1.4 JVM时关注的一个方面,它在反射方法调用结果中显示。在这类操作的性能方面,Sun 1.4.1 JVM显示了比1.3.1版本很大的改进。


如果为为创建使用反射的对象编写了类似的计时测试程序,我们会发现这种情况下的差异不象字段和方法调用情况下那么显著。使用newInstance()调用创建一个简单的java.lang.Object实例耗用的时间大约是在Sun 1.3.1 JVM上使用new Object()的12倍,是在IBM 1.4.0 JVM的四倍,只是Sun 1.4.1 JVM上的两部。使用Array.newInstance(type, size)创建一个数组耗用的时间是任何测试的JVM上使用new type[size]的两倍,随着数组大小的增加,差异逐步缩小。

0 个回复

您需要登录后才可以回帖 登录 | 加入黑马