LSM树在RocksDB、LevelDB、HBase的具体实现

637 阅读2分钟

携手创作,共同成长!这是我参与「掘金日新计划 · 8 月更文挑战」的第7天,点击查看活动详情 >>

RocksDB

image.png

RocksDB的写缓存(即LSM树的最低一级)名为memtable,对应HBase的MemStore;读缓存名为block cache,对应HBase的同名组件。

执行写操作时,先同时写memtable与预写日志WAL。memtable写满后会自动转换成不可变的(immutable)memtable,并flush到磁盘,形成L0级sstable文件。sstable即有序字符串表(sorted string table),其内部存储的数据是按key来排序的,后文将其简称为SST。

执行读操作时,会首先读取内存中的数据(根据局部性原理,刚写入的数据很有可能被马上读取),即active memtable→immutable memtable→block cache。如果内存无法命中,就会遍历L0层sstable来查找。如果仍未命中,就通过二分查找法在L1层及以上的sstable来定位对应的key。

随着sstable的不断写入,系统打开的文件就会越来越多,并且对于同一个key积累的数据改变(更新、删除)操作也就越多。由于sstable是不可变的,为了减少文件数并及时清理无效数据,就要进行compaction操作,将多个key区间有重合的sstable进行合并。

LevelDB

image.png

  1. Append到日志中,保持持久性≈顺序写

  2. 记录插入内存中的mutable Memtable(skiplist保证记录有序)

  3. Memtable达到一定大小之后,变成immutable Memtable

  4. 条件,后台的Compaction线程dump到磁盘(level0 中的sstable)

    • 内存是有限的,不能把数据都放在内存中
    • 断电后内存中的数据会全部丢失,日志虽可以恢复数据,但不能全部恢复
  5. level L中的tables达到一定大小之后,level L里面选取一些table与level L+1中有key重叠的table进行compaction,生成新的table

    • 达到比较好的读性能——读取较小的文件,减少重叠
    • 降低compaction的IO开销——进行分层设计

HBase

image.png

HFile就是LSM树中的高层实现。从逻辑上来讲,它是一棵满的3层B+树,从上到下的3层索引分别是Root index block、Intermediate index block和Leaf index block,对应到下面的Data block就是HFile的KeyValue结构了。

参考

LSM Tree-Based存储引擎的compaction策略 
从B+树到LSM树,及LSM树在HBase中的应用