【问题标题】:How to work around I/O bottleneck when writing to multiple files using multiple threads使用多线程写入多个文件时如何解决 I/O 瓶颈
【发布时间】:2011-11-16 06:27:30
【问题描述】:

我目前有一个多线程程序,可以抓取网站并将其文本写入文件。 CPU 方面,我可以同时运行大量线程,但很快 I/O 就会成为瓶颈。我在想我可以让每个线程写入一个数组阻塞队列,但我知道我将生成超过可用的 32GB 内存。有没有办法在数组达到一定大小后将其转储到文本文件中,以便我可以释放该空间?还是有其他方法可以解决我遗漏的这个 I/O 问题?

【问题讨论】:

  • 你不能只使用集合并序列化它吗?然后你只需交换你正在写入的对象。
  • 我会创建一个线程,它是您对阵列的看门人。访问具有某些功能的数组。如果数组达到一定大小,则启动工作线程,将部分数组写入磁盘。只需使用一个线程,b/c 你的文件将是线性的(如果你保持简单的话),磁盘可能是你的瓶颈,而不是 CPU。

标签: java multithreading performance file-io


【解决方案1】:

让我们来一张图片,它有 SATA 2 控制器,它允许以每秒 300 MB 的速度写入。现在的问题是我们想象中的计算机的 Internet 连接带宽是多少。我知道以太网适配器支持的生产中最后一个最大带宽是每秒 1 GB。但是我认为这样的互联网连接带宽非常昂贵(我什至怀疑某些商业主机是否支持它)。我认为每秒 300 MB 的 Internet 连接就足够了。让我们的电脑有这样一个。

结果是

      Input (300 MB/s);

      Writing (300 MB/s).

简历:如果你想上网下载,你必须增加连接数和磁盘以及磁盘控制器。否则 300 MB/s 看起来相当不错。线程对您没有帮助。 CPU 和内存也与我们的问题无关。

【讨论】:

    【解决方案2】:

    我不会有“吨”的线程在运行。我会在特定系统上使用不同数量的线程进行分析,直到找到提供最大吞吐量的读取器线程数。我怀疑这个数字会很小。基本上,您只需要在等待其他服务器响应时让 CPU 保持忙碌即可。

    对于您要写入的每个物理驱动器,我都会有一个写入器线程。使用有限大小的BlockingQueue 将读取线程连接到写入线程;如果读取器距离磁盘太远,这将限制他们的活动。

    【讨论】:

      【解决方案3】:

      我猜是磁盘 I/O 是瓶颈,因为要处理这么多文件,是吗?您可以一次写入整个文件吗?爬取站点,将缓冲区添加到缓冲区集合,然后将缓冲区集合排队到一个文件写入线程?顺序写入会提高磁盘性能,是吗?如果缓冲整个站点不可行,那么您可以在每个站点收集足够的缓冲区实例以使磁盘写入值得(我不知道,当收集的总数超过 64K 时说),然后将集合从写入器线程排队并开始收集一组新的缓冲区。

      改善多文件写入延迟的简单方法 - 获得 SSD。

      【讨论】:

        【解决方案4】:

        使用更少的线程!他们不会给你买太多东西。整个问题的一端是网络绑定,另一端是磁盘绑定。真正涉及的 CPU 并不多。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2014-01-02
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2015-11-26
          相关资源
          最近更新 更多