【发布时间】:2013-01-13 15:51:24
【问题描述】:
我认为只有两个级别(level-0 和 level-1)就可以了,为什么 LevelDB 需要 level-2、level-3 等等?
【问题讨论】:
我认为只有两个级别(level-0 和 level-1)就可以了,为什么 LevelDB 需要 level-2、level-3 等等?
【问题讨论】:
我将向您指出有关 LevelDB 及其底层存储结构的一些文章的方向。
所以在documentation for LevelDB 它讨论了级别之间的合并。
这些合并具有将新更新从年轻级别逐渐迁移到最大级别的效果,仅使用批量读取和写入(即,最大限度地减少昂贵的查找)。
LevelDB 的结构类似于Log Structured Merge Trees。如果您有兴趣对其进行分析,本文将讨论不同的级别。如果你能理解数学,那么理解数据结构似乎是你最好的选择。
levelDB 的analysis 更容易阅读,它谈到了数据存储与 LSM 树的关系,但就您对级别的问题而言,它所说的只是:
最后,拥有数百个磁盘上的 SSTable 也不是一个好主意,因此我们会定期运行一个进程来合并磁盘上的 SSTable。
LevelDB 文档可能提供了最好的答案:(最大化写入和读取的大小,因为 LevelDB 是在磁盘上(慢速查找)数据存储)。
祝你好运!
【讨论】:
我认为这主要与简单快速的关卡合并有关。
在 Leveldb 中,level-(i+1) 大约有。 10 倍于 level-i 的数据。这更类似于多级缓存结构,如果数据库在键 x1 到 x2 之间有 1000 条记录,则该范围内最常访问的 10 个将位于级别 1 中,而同一范围内的 100 条记录将是在第 2 级,在第 3 级休息(这并不准确,只是为了直观地了解关卡)。在此设置中,要合并级别-i 中的文件,我们需要查看级别-(i+1) 中的最多 10 个文件,并且可以将它们全部放入内存中,快速合并完成并写回。这导致为每个压缩/合并操作读取相对较小的数据块。
另一方面,如果您只有 2 个级别,则一个级别 0 文件中的键范围可能会匹配级别 1 中的 1000 个文件,并且所有这些文件都需要打开以进行合并,这将是相当不错的慢的。请注意,这里的一个重要假设是我们有固定大小的文件(比如 2MB)。使用级别 1 中的可变长度文件,您的想法仍然有效,我认为 HBase 和 Cassandra 等系统中使用了这种变体。
现在,如果您担心多级查找延迟,这又类似于多级缓存结构,最近写入的数据将位于更高级别,以帮助典型的参考局部性。
【讨论】:
级别 0 是内存中的数据,其他级别是磁盘数据。重要的部分是对级别中的数据进行排序。如果 level1 包含 3 个 2Mb 文件,那么在 file1 中,它是 file2 150..200 和 file3 300..400 中的键 0..50(已排序)(例如)。因此,当内存级别已满时,我们需要以最有效的方式将其数据插入磁盘,即顺序写入(使用尽可能少的磁盘寻道)。想象一下,在内存中我们有 60-120 键,很酷,我们只是将它们按顺序写入文件,然后在 level1 中变成 file2。非常有效率! 但是现在想象 level1 比 level0 大得多(这是合理的,因为 level0 是内存)。在这种情况下,level1 中有很多文件。现在我们在内存中的键(60-120)属于许多文件,因为 level1 中的键范围非常细。现在要将 level0 与 level1 合并,我们需要读取许多文件并进行大量随机搜索,在内存中创建新文件并写入它们。所以这就是多层次想法发挥作用的地方,我们将有很多层,每一层都比前一个(x10)大一些,但不会大很多,所以当我们必须将数据从 i-1 迁移到第 i 层时,我们有一个很有可能必须读取最少的文件。
现在,由于数据可能会更改,因此可能无需将其传播到更高更昂贵的层(可能会更改或删除),因此我们完全避免了昂贵的合并。最终进入最后一层的数据在统计上变化的可能性最小,因此最适合最昂贵的与最后一层合并。
【讨论】: