【问题标题】:System.out.print causing latency? [duplicate]System.out.print 导致延迟? [复制]
【发布时间】:2016-04-25 14:18:39
【问题描述】:

我有一个从我的 Java 编程书中得到的简单程序,只是添加了一点。

package personal;

public class SpeedTest {
  public static void main(String[] args) {
    double DELAY = 5000;
    long startTime = System.currentTimeMillis();
    long endTime = (long)(startTime + DELAY);
    long index = 0;

    while (true) {
      double x = Math.sqrt(index);
      long now = System.currentTimeMillis();
      if (now >= endTime) {
        break;
      }
      index++;
    }
    System.out.println(index + " loops in " + (DELAY / 1000) + " seconds.");
  }
}

这将返回128478180 loops in 5.0 seconds.

如果我在 if 语句之前添加 System.out.println(x);,那么我在 5 秒内的循环次数会下降到 400,000 次,这是因为 System.out.println() 的延迟吗?还是只是x在我没有打印出来的时候没有被计算出来?

【问题讨论】:

  • 打印到控制台必须是您可以在性能方面做的最糟糕的事情。 IO 操作需要很多时间。
  • System.out.println 是一个 IO 操作,是的,它可以影响任何程序的性能
  • 问得好问题,我不明白反对意见。仅仅因为它对你来说微不足道,并不意味着你应该投反对票。
  • 为了比较,你可以在循环中使用StringBuilderappend(x),然后打印出来......

标签: java printing latency


【解决方案1】:

任何时候你在一个非常繁忙的循环中“输出”,在任何任何编程语言中,你都会引入两个可能非常显着的延迟:

  1. 必须将数据转换为可打印字符,然后将其写入可能要发送到的任何显示器/设备……然后……
  2. “输出任何东西”的行为要求进程与可能也生成输出的任何其他进程同步。

经常用于此目的的另一种策略是“跟踪表”。这是一个内存中的数组, 有一些固定大小,其中包含字符串。条目以“循环”方式添加到此表中:最旧的条目不断被最新的条目替换。这个策略提供了一个历史而不需要输出。(剩下的唯一要求是任何向表中添加条目或从中读取的人都必须同步他们的活动例如使用互斥体。)

希望显示跟踪表内容的进程应该获取互斥体,在内存中复制感兴趣的内容,然后在准备输出之前释放互斥体。这样,为跟踪表贡献条目的各个进程将不会被与 I/O 相关的延迟源延迟。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2020-09-23
    • 2014-04-24
    • 1970-01-01
    • 1970-01-01
    • 2016-12-19
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多