0

这是代码片段:

https://gist.github.com/987751

对我来说,它有时像:

java-客户端:
  for 循环占用:23
  方法调用次数:19

java-服务器:
  for loop take: 0 # 更快,正如预期的那样
  方法调用采用:48 # 较慢 - 预期?

所以第一个问题是“为什么它比客户端 VM 慢”

另外我猜下一个问题是“是否有可能为方法调用方式获得超 0ms 的加速(它几乎是相同的代码)?”

我还认为,尽管有这种奇怪之处,但热点通常运行得更快,即使有匿名类等?

谢谢!

-罗杰-

4

1 回答 1

2

这一切都与 Hotspot 的两种口味如何调整有关:

  • 客户端已针对快速启动进行了调整。它 JIT 会立即“几乎”编译方法。

  • 在假定为长时间调整的服务器实例的生命周期内,服务器被调整为更高(更好)的吞吐量。它让解释器在 JIT 编译它们之前运行更长时间(收集使用统计信息)。然后(我相信)它会执行更积极的优化......这需要更长的时间。

相关答案:“java -server”和“java -client”之间的真正区别?

顺便说一句,它是运行客户端和服务器模式的同一个 Hotspot JVM。AFAIK,差异是由于两种模式选择了不同的默认 JVM 调整/配置参数。


所以第一个问题是“为什么它比客户端 VM 慢”

我不知道。

也许客户端模式启用了真正有助于这个(高度人工)基准测试的特定优化。或者也许其中一个服务器模式优化实际上是针对这个(高度人为的)基准的反优化。如果你真的想知道,让 JIT 编译器转储原生代码并详细分析。(但我认为这是浪费时间。)

另外我猜下一个问题是“是否有可能为方法调用方式获得超 0ms 的加速(它几乎是相同的代码)?”

这很容易。优化器发现方法调用不会影响其他任何东西,并优化了调用。然后也可以优化循环。

我还认为,尽管有这种奇怪之处,但热点通常运行得更快,即使有匿名类等?

我认为你不应该假设任何事情。

但是,我也不认为您的微基准对真实程序有任何意义。一般来说,微基准往往会产生误导,而你的有缺陷(例如,被优化掉的循环)并且似乎没有测试典型的(编写良好的)Java 程序会做的事情。

如果您真的关心 HotSpot 的两种模式的相对性能,您应该在真实数据上运行并测量您的应用程序的性能。

...为什么服务器 JVM 会选择看起来更糟的东西?

优化器旨在优化实际程序……而不是花时间做与有用计算没有任何相似之处的奇怪事情的微基准。并非所有优化在所有情况下都是有益的,您可能遇到了某种极端情况。

但这只有在您在实际应用程序中看到同样的事情发生时才有意义。


最后,您没有提供有关您的 JVM 版本、平台和硬件的任何详细信息。这些事情可能会对相对绩效指标产生巨大影响。

于 2011-05-23T23:02:24.733 回答