有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

性能java,时间独立的if语句和循环,而不是带有探查器的方法

我使用像VisualVM这样的工具来分析我的方法,以找到需要返工的慢方法,从而使它们更快,但我似乎找不到任何能够对方法中的单个循环或代码块计时的分析器

现在我不得不求助于手动计时>

long sTime = System.currentTimeMillis();
//my Code here
System.out.println("time=" + ((System.currentTimeMillis() - sTime)));

但这真的很乏味,因为我必须为每个循环/if/codeblock手动添加和删除计时器,以获得细粒度的计时数据。我想知道是否有任何工具可以分析代码块,或者某种eclipse插件可以自动添加和删除计时器。我使用过代码模板,但它还远远不够完美

我确信,我不是唯一一个想要更优雅的细粒度分析解决方案的人


共 (2) 个答案

  1. # 1 楼答案

    你说(实际上)你想知道如何让你的代码运行得更快。 这是大多数人想做的。 有一种简单的方法根本不需要分析器

    如果代码正在做一些不需要做的事情,并且您摆脱了这些事情,那么您的代码只能在相同的硬件上运行得更快。没有别的办法了
    删除它(我们称之为K)将节省一些时间。我们假设是30%

    这意味着,如果您有一种方法来获取随机时间堆栈样本,比如使用jstack或者简单地将其暂停在调试器中并显示堆栈(可能还有一些数据),那么该样本在K.“至少”期间发生的概率至少为30%,因为它实际上可能花费50%的时间,而修复只节省30%
    如果你这样做10次,你可以期望看到K大约3次(或更多)

    那么就做10次
    每个堆栈示例将向您展示堆栈上的每个函数和代码行,如果您阅读了它,您将完全了解它当时在做什么,以及为什么要这样做
    在堆栈的任何级别上查找任何可以做得更好的内容
    如果您看到一件可以做得更好的事情,并且您在多个样本上看到它,那么您已经找到了K.
    事实上,它的百分比越大,需要多次查看的样本就越少
    修复它,然后使用计时器查看结果

    然后你可以重新做一遍,以获得下一次加速
    当你找不到更多的时候,你的代码基本上是最优的

    这可能会令人惊讶,但这可以发现任何分析器都能找到的任何加速,有些则是他们无法找到的。
    它叫random pausing,很多人都依赖它

    有些人说这正是剖析者所做的,只是更好,但他们需要考虑一下。 即使是对堆栈进行采样(具有行级精度)的好分析器,在墙上时钟时间上的问题是,它们有一个后端,可以对热路径、调用图、火焰图、“总时间”、“自时间”进行汇总。。。无论什么 我们鼓励您查看这些,而不是实际样品本身
    This post显示了在这些摘要中隐藏加速是多么容易,以及为什么这是一件坏事
    这些示例就是可以告诉您发生了什么可以做得更好的洞察力所在,如果需要足够的时间来修复,则不需要大量的示例来查看
    如果你想知道为什么,the math is here.


    回应评论:

    你在正确的轨道上。你知道它在无限循环或接近无限循环中工作,因为这样的问题需要99.99%的时间,所以你的停顿肯定会在其中。如果这个问题花费的时间较少,比如30%甚至10%,它也能起作用

    如果这个问题花费的时间不多,那么平均每1/F个样本你就会看到它。 例如,如果F为0.3(30%),则平均每1/0.3=3.33个样本就会看到它。 但是,如果只看到一次可疑代码,并不意味着这是个问题。 但是,如果您看到它两次(或更多),那么您肯定知道这是一个加速的机会。 两次查看问题所需的平均样本数为2/F,如果F为30%,则为6.67个样本。 所以只要继续采样,直到你两次看到可疑代码

    如果代码运行得太快,没有问题。只要在它周围放一个长循环。如你所说,假设需要3微秒。你所要做的就是循环10^7次,需要30秒。 如果其中有一个加速机会占30%的时间,那么无论它有多快,每次暂停都有30%的机会显示它。 您不必担心代码速度太快

    你想节省70%的时间。要做到这一点,可能需要多次修复。假设有30%、20%、10%和10%的潜在加速。去掉30%的一个,其他的分别扩大1.43%到29%、14%和14%。去除29%是1,现在是20%和20%。去掉下一个,最后一个是25%。这就是你如何获得巨大的加速-剥离了

    下面是最底层最重要的一点: 从中可以看出,不要错过任何一个是多么重要。 四分之三,少了一分,将不会减少芥末。 Speedup opportunities can easily hide from profilers' summaries,但它们无法在堆栈样本中隐藏。 忘记所有奇特的分析器结果,你需要速度,这就是底线

  2. # 2 楼答案

    对于编写微基准测试,应该使用适当的工具,例如JMH。使用正确的工具进行基准测试也可以避免the common pitfalls