我有上的位集合执行位操作一些Java代码。我操作的列表,并且可以通过遍历他们“解读”出来的,但它是对我很重要,我可以尽可能快地执行这些操作,所以我一直在试图动态生成的代码应用它们。我生成Java源来执行操作和编译执行使用了Javassist那些操作的类。

不幸的是,我的动态生成的代码的运行速度比解释代码要慢。看来,这是因为热点优化解释代码,但没有优化的编译代码:我跑这几千次后,我的解释代码运行速度的两倍,因为它没有开始,但我的编译后的代码没有显示出加速。与此假设一致,我的解释代码最初是比编译代码慢,但最终是要快。

我不知道为什么会这样。我的猜测是,也许Javassist所使用的类加载器,其类热点不接触。但我不是类加载在Java专家,所以我不知道这是否是一个合理的猜测或如何去测试它。下面是我如何创建和使用了Javassist加载类:

ClassPool pool = ClassPool.getDefault();
CtClass tClass = pool.makeClass("foo");

// foo implements MyInterface, with one method
tClass.addInterface(pool.get(MyInterface.class.getName()));

// Get the source for the method and add it
CtMethod tMethod = CtNewMethod.make(getSource(), tClass);
tClass.addMethod(tMethod);

// finally, compile and load the class
return (MyInterface)tClass.toClass().newInstance();

有没有人有一个想法,什么是怎么回事?我真的很感激力所能及的帮助,你可以给。

我使用Windows XP 32位的太阳1.6服务器JVM。

有帮助吗?

解决方案

热点不关心在码来自。例如,它会通过与由不同的类加载器加载的实现的虚拟方法调用称为愉快地内联代码。

我建议你写出来的源代码,您要为这个基准进行操作,然后基准,。它通常更容易编写出的生成代码示例而非反正写发生器。

有许多原因热点可能不优化代码难,因为它可能。例如很长的方法将趋向于不被内联或已方法联到它们。

其他提示

我想我明白了什么是怎么回事。我的第一个错误是产生这太长的方法。我固定在此之后,我注意到尽管我的生成的代码仍然较慢,它最终走近解释代码的速度。

我认为,最大的加速比这里来自热点优化我的代码。在解释的版本,有很少的代码进行优化,使热点迅速照顾它。在生成的版本,有很多的代码进行优化,所以热点需要更长的时间对所有的代码工作它的魔力。

如果我跑我的基准足够长的时间,我现在看到我生成的代码执行只比解释代码稍微好一点。

有一个JVM设置控制代码是如何快速应当编译-XX:CompileThreshold = 10000

  

在编译之前的方法调用/分支数[-client:1500]

我不知道这是否会帮助,因为在你的榜样,大小似乎起着至关重要的作用。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top