2

在基于内存的计算模型中,通过考虑数据结构,可以抽象地完成唯一需要完成的运行时间计算。

但是,关于高性能磁盘 I/O 算法的文档并不多。因此,我提出以下一组问题:

1) 我们如何估计磁盘 I/O 操作的运行时间?我假设我们可以添加一组简单的常量来在磁盘上而不是在内存中查找值...

2)更具体地说,访问文件中特定索引的性能有什么区别?这是一个恒定时间操作吗?还是取决于指数“下降”多远?

3) 最后... JVM 如何优化对文件索引部分的访问?

而且......就资源而言 - 一般来说......是否有任何用于磁盘数据结构实现的好的习语或库?

4

5 回答 5

2

1)如果需要比较各种IO函数的速度,只需要运行一千次,记录运行时间。

2)这取决于您计划如何达到此索引。文件开头的索引与文件中间的索引完全相同。它只是指向磁盘上的一段内存。如果您通过从头开始并在那里进行到该索引,那么是的,这将需要更长的时间。

3/4)不,这些是由操作系统本身管理的。Java 的底层不足以处理这些类型的操作。

于 2012-10-20T03:53:41.617 回答
2

1) 我们如何估计磁盘 I/O 操作的运行时间?我假设我们可以添加一组简单的常量来在磁盘上而不是在内存中查找值...

在《计算机系统:程序员的视角》的第 6 章中,他们给出了一个非常实用的数学模型,说明从典型磁盘读取一些数据需要多长时间。

要引用链接的 pdf 中的最后一页:

Putting it all together, the total estimated access time is
Taccess = Tavg seek + Tavg rotation + Tavg transfer
        = 9 ms      + 4 ms          + 0.02 ms
        = 13.02 ms

This example illustrates some important points:
• The time to access the 512 bytes in a disk sector is dominated by the seek time and the rotational
latency. Accessing the first byte in the sector takes a long time, but the remaining bytes are essentially
free.
• Since the seek time and rotational latency are roughly the same, twice the seek time is a simple and
reasonable rule for estimating disk access time.

*注意,链接的 pdf 来自作者网站 == 没有盗版

当然,如果正在访问的数据是最近访问过的,那么它很有可能缓存在内存层次结构中的某个地方,在这种情况下,访问时间非常短(实际上,与磁盘访问时间相比,“接近即时”)。

2)更具体地说,访问文件中特定索引的性能有什么区别?这是一个恒定时间操作吗?还是取决于指数“下降”多远?

如果寻找的位置没有在附近按顺序存储,则可能会发生另一个寻找+旋转的时间量。这取决于您要查找的文件中的哪个位置,以及该数据物理存储在磁盘上的哪个位置。例如,碎片文件保证会导致磁盘寻道读取整个文件。

需要记住的是,即使您可能只请求读取几个字节,物理读取也往往以固定大小的块(扇区大小)的倍数发生,最终进入缓存。因此,您稍后可能会搜索文件中的某个附近位置,并幸运地发现它已经在缓存中。

顺便说一句-如果您对该主题感兴趣,那本书中有关内存层次结构的整章都是纯金的。

于 2012-10-20T17:12:26.120 回答
1

1) 我们如何估计磁盘 I/O 操作的运行时间?我假设我们可以添加一组简单的常量来在磁盘上而不是在内存中查找值...

没有这样的通用常数。事实上,物理磁盘 I/O、文件系统和操作系统的性能模型过于复杂,无法对具体操作做出准确的预测。

2)更具体地说,访问文件中特定索引的性能有什么区别?这是一个恒定时间操作吗?还是取决于指数“下降”多远?

预测太复杂了。例如,它取决于操作系统缓冲的文件量、物理磁盘参数(例如寻道时间)以及操作系统如何有效地调度磁盘活动……跨所有应用程序。

3)最后......JVM如何优化文件索引部分的访问?

它没有。这是操作系统级别的东西。

4) 磁盘数据结构实现有什么好的习语或库吗?

如果没有您的实际需求的更多细节,这很难回答。但最好的想法是不要自己尝试和实施这种事情。找到一个非常适合您的要求的现有库。

于 2012-10-20T02:48:41.500 回答
1

高性能磁盘 I/O 算法。

硬件的性能通常非常重要,以至于你在软件中所做的事情并不重要。您应该首先考虑为这项工作购买合适的硬件。

我们如何估计磁盘 I/O 操作的运行时间?我假设我们可以添加一组简单的常量来在磁盘上而不是在内存中查找值...

为它们计时很简单,因为它们总是要花费很多微秒。例如,HDD 可以执行 80-120 IOP,SSD 可以执行 80K 到 230K IOP。您通常可以轻松获得制造商指定的 1/2,而获得 100% 是您可以在软件中使用技巧的地方。无论如何,除非您有大量内存并且只读取数据,否则您将永远无法让 HDD 像 SSD 一样运行,在这种情况下,操作系统将为您完成所有工作。

您可以购买具有 HDD 容量但性能接近 SSD 的混合驱动器。对于商业生产用途,您可能愿意花钱购买具有多个驱动器的磁盘子系统。这可以将性能提高到 500 IOPS,但成本会显着增加。您通常购买磁盘子系统,因为您需要它提供的容量和冗余,但您通常也会获得性能提升,但有更多的脊椎一起工作。尽管这个关于磁盘子系统性能的链接是旧的(2004 年),但从那时起它们并没有太大变化。

更具体地说,访问文件中特定索引的性能有什么区别?这是一个恒定时间操作吗?还是取决于指数“下降”多远?

这取决于它是否在内存中。如果它与您最近读取的数据非常接近,则很可能,如果它很远,则取决于您过去所做的访问以及您有多少可用内存来缓存磁盘访问。

HDD 的典型延迟为每个约 8 毫秒(即,如果您有 10 个随机读取排队,则可能为 80 毫秒) SSD 的典型延迟为 25 到 100 微秒。读取已经排队的可能性要小得多,因为它开始时要快得多。

JVM 如何优化对文件索引部分的访问?

假设您使用的是合理的缓冲区大小,那么您在软件中通常无能为力。您可以做的是由操作系统完成。

磁盘数据结构实现有什么好的习语或库吗?

使用合理的缓冲区大小,例如 512 字节到 64 KB。

更重要的是,根据您的要求购买合适的硬件。

于 2012-10-20T08:41:12.713 回答
1

另请注意,Linux 系统至少允许不同的文件系统。根据应用程序,一个可能比其他的更适合。http://en.wikipedia.org/wiki/File_system#Linux

于 2012-10-24T15:32:05.250 回答