只需这一篇博客就能完全弄懂LSM树

早期LSM树

为什么需要LSM树

B+树的数据都存储在叶子节点中,而叶子节点一般都存储在磁盘中。因此,每次插入的新数据都需要随机写入磁盘,而随机写入的性能非常慢。如果是一个日志系统,每秒钟要写入上千条甚至上万条数据,这样的磁盘操作代价会使得系统性能急剧下降,甚至无法使用。
针对这种频繁写入的场景,提出一种常见的设计思路和检索技术:LSM树。
LSM树是近年来许多火热的NoSQL数据库中使用的检索技术。

如何使用批量写入代替多次随机写入

操作系统对磁盘的读写是以块为单位的,我们也可以以块为单位写入,而不是每次插入一个数据都要随机写入磁盘。
LSM树根据上面这个思路设计这样一个机制:
当数据写入时,延迟写磁盘,将数据先存放在内存中的树里,进行常规的存储和查询。当内存中的树持续变大达到阈值时,再批量地以块为单位写入磁盘的树中。因此LSM树至少需要由两棵树组成,一棵是存储在内存中较小的C0树,另一课时存储在磁盘中较大的C1树。
在这里插入图片描述
C1存储在磁盘,因此我们可以直接使用B+树来生成。那对于全部存储在内存中的C0树,该如何生存?在数据都能加载在内存中的时候,B+树并不是最合适的选择,它的效率并不会更高。因此,C0树我们可以选择其他的数据结构来实现,比如平衡二叉树甚至跳表。我们先假设C0树也是一棵B+树。相比于普通的B+树,C0,C1树有一个特点就是所有叶子节点都是满的,因为C1树不需要支持随机写入了,我们完全可以等内存中的数据写满一个叶子节点之后,再批量写入磁盘,因此每个叶子节点都是满的,不需要预留空位来支持新数据的随机写入。

如何将内存数据与磁盘数据合并

解决了内存中数据备份的问题,我们就可以接着写入数据了。内存中C0树的大小是有上限的当C0树被写满之后,怎么把它转化到磁盘的C1树上呢?这就涉及滚动合并的过程了。我们可以参考两个有序链表归并排序的过程,将C0树和C1树的所有叶子节点中存储的数据看作是两个有序链表,那滚动合并问题就变成了我们熟悉的两个有序链表的归并问题。
在这里插入图片描述
由于磁盘具有顺序读写效率高的特性,因此,为了提高C1树中节点的读写性能,除了根节点以外的节点都要尽可能地存放到连续的块中,让它们能作为一个整体单位来读写,这种包含多个节点的块就叫作多页块

滚动归并:

  • 第一步,以多页块为单位,将C1树的当前叶子节点从前往后读入内存。读入内存的多页块,叫做清空块,意思是处理完以后会被清空。
  • 第二步,将C0树的叶子节点清空块中的数据进行归并排序,把归并的结果写入内存的一个新块中,叫作填充块
  • 第三步,如果填充块写满了,我们就要将填充块作为新的叶节点顺序写入磁盘。这个时候,如果C0树的叶子节点和清空块都没有遍历完,我们就继续遍历归并,将数据写入新的填充块。如果清空块遍历完了,我们就去C1树中顺序读取新的多页块,加载到清空块中。
  • 第四步,重复第三步,直到遍历完C0树和C1树的所有叶子节点=,并将所有的归并结果写入到磁盘。这个时候,我们可以同时删除C0树和C1树中被处理过的叶子节点。这样就完成了滚动归并的过程。
    在C0树到C1树的滚动归并过程中,你会看到,几乎所有的读写操作都是以多页块为单位,将多个叶子节点进行顺序读写的。而且,因为磁盘的顺序读写性能和内存是一个数量级的,这使得LSM树的性能得到了大幅度的提升。

LSM树是如何检索的?

因为同时存在C0和C1树,所以要查询一个key时,我们会先到C0树中查询。如果查询到了则直接返回,不用再去查询C1树了。
而且C0树会存储最新的一批数据,所以C0树中的数据一定会比C1树中的新。因此如果一个系统的检索主要是针对近期数据的,那么大部分数据我们都能在内存中查到,检索效率会非常高。
那如果我们在C0树种没有查询到key呢?那这个时候系统就会去磁盘中的C1树查询,在C1树种查到了,我们能直接返回吗?如果没有特殊处理的话其实不能。
比如如果一个数据已经被写入系统,并且我们也把它写入C1树了。但是,在最新的操作中,这个数据被删除了,那我们自然不会在C0树中查询到这个数据。可是它依然存在于C1树中。这种情况下,我们在C1树中检索到的就是过期的数据。既然是过期的数据,那为了不影响检索结果,我们能否从C1树中将这个数据删除呢?删除的思路没有错,但是我们不希望对C1树进行随机访问,这时我们该怎么处理?
我们依然可以采取延迟写入和批量操作的思路。对于被删除的数据,我们会将这些数据的key插入到C0树中,并且存入删除标志。如果C0树中已经存有这些数据,我们就将C0树中这些数据对应的key都加上删除标志。这样一来,当我们在C0树中查询时,如果查到了一个带着删除标志的key就直接返回查询失败,我们也就不用去查询C1树了。在滚动归并的时候,我们会查看数据在C0树中是否带有删除标志。如果有,滚动归并时将它放弃。这样C1树就能批量完成数据删除操作。(标记删除的数据时在merge合并的时候被物理删除的

LSM树的使用场景

在写大于读的应用场景下,尤其在日志系统和监控系统这类应用中,我们可以使用基于LSM树的NoSQL数据库,这是比B+树更适合的技术方案。

LSM树具有以下三个特定:

  • 将索引分为内存和磁盘两个部分,并在内存达到阈值时启动树合并
  • 用批量写入代替随机写入,并且用预写日志WAL技术保证内存数据在系统崩溃后可以被恢复
  • 数据采用类似日志追加写的方式写入磁盘,以顺序写的方式提高写入效率

LSM树的这些特定,使得它相对于B+树,在写入性能上有大幅提升。所以,许多NoSQL系统都使用LSM树作为检索引擎,而且还对LSM树进行了优化以提升检索性能。

小总结

B+树是写入的时候就找好key的位置,读取的时候直接根据索引查找key的值
LSM是写入是可能一个key存在不同层的树上,读取的时候,需要合并key不同树上的值。
相当于B+树是写入时merge,LSM是读取时候merge

现代LSM树

早期LSM树:
实质就是利用内存,延迟写入磁盘的时机。
C0-tree 由于常驻内存,检索起来不会产生 IO,所以理论上,我们可以使用各种可用于高效索引的数据结构来存储数据,比如红黑树、跳表等等。但是因为内存成本高昂,能存储的数据必然有限,更大量的数据仍然需要存储在磁盘里。而磁盘中的 C1-tree 一般被实现为特殊的 B+ 树。数据的存储也会分为两个阶段,我们会一直先在内存中存储元素,直到内存中的数据到达一个阈值,我们会开始和 C1-tree 中的节点进行合并和覆写,过程和多路归并有点相似。因为我们可以决定写入磁盘的时机,所以完全可以保证 B+ 树的所有节点是满的,也就避免了许多单次的随机写操作
现代LSM树包含三个部分:memtable、immutable memtable、SSTable
前两个在内存中,最后一个在磁盘中。我们会先把临时地数据写在memtable中,然后在合适的时机刷入磁盘的SSTable中。(WAL机制保证数据安全)

Memtable

内存中的数据结构,存储的是近期更新的记录值,类似原始LSM树,可用各种高效的数据结构实现,比如跳跃表,红黑树。
在这里插入图片描述

Immutable Table

在 Memtable 存储的元素到达一个数量级之后,我们就会把它固化成 immutable table,从字面上理解,就是不可变表
memtable 的拷贝操作,拷贝过程需要时间,但同时我们的系统很可能在对外工作,所以创建副本可以很好的帮助我们避免读写冲突竞争,从而避免阻塞,提高性能。
顺序写入磁盘,SSTable不再发生变化
在这里插入图片描述
在这里插入图片描述

SSTable

SSTable不可变,因此对现有对象Key的更新不会覆盖现有的SSTable
当下我们有了内存中的有序结构,存储了近期的记录变更,如何把数据落盘,既要有磁盘顺序读写的优势,也能保证所写的格式便于改动也便于查询。
它是整个 LSM Tree 的核心,毕竟我们的大部分数据都是存储在磁盘上的,SSTable 就是在磁盘上做持久化的部分。本质其实很简单,就是一段段按照 key 有序排列的键值对
在这里插入图片描述
SSTable 一般也会带上一个索引文件,值存储的是 key 所对应的 offset,加载到内存后,我们利用二分搜索可以很快查找出要访问的 key 的值。
最简单的持久化方式就是我们在磁盘上把内存中有序的键值对直接 dump 成一个个段,也就是 segment。后面存储的段和前面存储的段,key 可能是重复的,因为后面的段新一些,所以在有重复的时候,最靠后的段中的记录值,就是某个 key 最新的状态。
我们把内存中有序的数据结构比如红黑树中的记录,dump 到一段磁盘上的空间,然后按 segment 一段一段往后叠加
在这里插入图片描述
那在这样的存储下,检索数据的时候需要怎么做呢?很简单,就是从后面的段开始,往前遍历,看看是否有查找到目标 key,有的话就返回。由于从后往前遍历,我们第一次查询到 key 的时候,一定就是这个 key 对应的最新状态。

但是这样存储会有很多问题:

  • 数据冗余很大,随着时间的推移,磁盘上会有大量重复的键。
  • 其次我们需要遍历每个有序的 segment,查看数据是否存在。随着数据量增大,最坏情况下,要遍历的 segment 会非常多,整个系统的查询效率显然是惨不忍睹的。
    总之就是读的速度慢过头了。
    压缩数据:
    前提:每个 segment 都是有序的,那我们显然可以比较高效地对多段数据进行合并操作,就是“多路归并”的思路,一般,多路归并的程序我们会在后台不断运行,我们会不断地把多个老的 segment 合并成一个更长的、同样有序的 segment
    在 SSTable 的主流实现里,我们会把不同的阶段被合并的 segment 放到不同的层中,并限制每一层数量当某层 segment 超过一定数量,我们就会把它们删除,合并出一个更大的 segment 放入下一层。
    低层中的 segment 显然是更新的记录值,更高层的则是更老的记录值。
    在这里插入图片描述
    在图的例子中可以看出来,我们合并 segment1、2、3 之后,在得到的 segment4 里,dog 的记录就只剩更新的 segment2 中的记录 84 了。这样我们的
    整个存储空间就不会无尽地膨胀
    ,最高的一层,最多也就是占用历史以来所有出现过的 key 和对应的记录值这样数量级的空间,而存储这些是数据库本应做到的。

更新和删除数据:

将数据标记成一种特殊的状态。这种通过标记而不是真实移除数据的方法,在业务开发中其实也很常见,有时候我们称为 soft delete。在有些 ORM 库中会直接通过 deleteAt 字段,标记删除时间,来表示这个数据被删除了,想恢复这个数据的时候也很简单,直接将 deleteAt 置空即可。
在 LSM tree 中也是一样,我们把这个特殊的状态称为== tombstone,墓碑==,看图就非常清楚了。
在这里插入图片描述
查询的时候,如果我们先查到了 tombstone,就可以认为数据已经不复存在了。
更新数据的时候也是,把原来key的数据标记为墓碑,如下图
在这里插入图片描述

小总结

  • 内存上的部分,memtable、immutable memtable,比较简单,用通用的有序集合存储即可,跳表、红黑树都是非常不错的选择;
  • 磁盘上的数据结构,SSTable,也不复杂,就是一段段连续按 key 有序存储的段,唯一需要做的就是后台启动一个程序不断地进行多路归并,得到分层的有序存储结构

每向下一级数据就会指数级增加

  • LSM树再内存中缓冲写入数据
  • 当缓冲区填满时,我们将其排序并作为不可变的SSTable刷新到磁盘
  • 随着更多缓冲区被刷新到磁盘,SSTable的数量也会增加
  • 会给读取带来问题,因此每次读取都必须搜索这些SSTable以执行查找。为了限制每次读取必须搜索的SSTable的数量,LSM树合并SSTable并在后台压缩它们。
    在这里插入图片描述

优化查找

查找key,会在每个级别SSTable上执行搜索,排序数据搜索快,但遍历所有磁盘SSTable会消耗大量I/O。
许多系统在内存中保留一个汇总表,其中包含每个level的每个磁盘块的最小key和最大key范围,允许系统跳过对那些key不在范围内的磁盘块的搜索。
另一个可能代价高昂的问题就是查找不存在的key,那就得扫描所有level中符合条件的磁盘块,因此大多数系统在每一层level都有一个布隆过滤器来防止这周情况。

chatgpt给的总结

-LSM(Log-Structured Merge Tree)树是一种新型的索引结构,与传统的 B+ 树相比,具有以下优点:

  1. 高写入性能。LSM 树采用了日志结构存储方式,所有的写操作都追加到磁盘顺序写日志中,不需要进行随机写入操作,因此具有较高的写入性能。
  2. 空间利用率高。LSM 树使用了合并机制,将多个较小的数据文件合并成一个较大的文件,避免了 B+ 树中频繁分裂和合并导致的空间浪费问题。

​ 但是,LSM 树也存在一些缺点:

  1. 查询性能较差。由于 LSM 树中的数据需要通过多层文件进行合并才能达到可用状态,因此查询操作的性能相对较低。
  2. 不支持范围查询。由于 LSM 树中的数据文件是按照时间顺序排列的,因此不支持范围查询。
  3. 内存占用较高。由于 LSM 树需要维护多个数据文件,因此需要占用较多的内存空间。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/20109.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

数据库/MySQL - 深入探究 - 1

1.应用场景 主要用于了解和掌握数据库/MySQL - 更新操作详细流程。 2.学习/操作 1.文档阅读 主要来自于AI的对话【geek chat, chatgpt】 以及官方文档资料,以及其他技术文章,专栏等。 2.整理输出 抛出问题: 数据库【这里以mysql…

EMQX在Windows系统下的开机自启与异常自动重启脚本

目录 0.前言 1.介绍 2.运行与停止 2.1 运行批处理程序 2.2 停止批处理程序 2.3 开机自启动 3.运行结果 4.详细介绍 5.前台运行版本 0.前言 由于为某万年老项目做运维,但源码遗失以及项目遗留问题导致emqx经常崩溃,故无法追根溯源,迫于…

量化工具使用介绍——Tushare

Tushare ID:497485 今年年初的时候,我和几位小伙伴一起合作打花旗杯,项目和量化交易有关。不可避免地会使用到一些常规的量化工具(尤其是python的第三方库),虽然决赛还没有开始,我们已经确定进入了二十强。…

BigQuant策略做量化真的能赚钱吗?

BigQuant策略做量化可以赚钱,但是是建立在一些前提条件基础之上的。量化策略本身存在的意义就是通过数量化模型建立科学投资体系,获取稳定收益,相比传统投资,其具备纪律性、系统性、及时性、准确性等诸多优势,所以一个…

自己做量化交易软件(45)小白量化实战18--直接使用通达信自编指标公式进行分析绘图和回测

自己做量化交易软件(45)小白量化实战18–直接使用通达信自编指标公式进行分析绘图和回测 小白量化一代提供了Python公式算法模式来写量化程序。 小白量化二代提供了仿通达信公式的模式来写量化程序。 小白量化三代除了仿通达信公式的模式来写量化程序外(见前几篇博客…

自己做量化交易软件(16)用小白通通量化AI框架打造自己的量化平台

最近一段时间&#xff0c;我主要学习python3和tkinter的窗口开发&#xff0c;对tkinter编程逐步了解。 此外&#xff0c;应广大朋友要求&#xff0c;我写了 一本学习python3学习书籍<小白学Python3实战搭建量化投资平台>. <小白学Python3实战搭建量化投资平台>内容…

Chat GPT是什么,初学者怎么使用Chat GPT,需要注意些什么

目录 Chat GPT是什么 初学者怎么使用Chat GPT 使用Chat GPT需要注意什么 一些简单的prompt示例 Chat GPT是什么 Chat GPT是由OpenAI开发的一种大型语言模型&#xff0c;它基于GPT&#xff08;Generative Pre-trained Transformer&#xff09;架构。GPT是一种基于深度学习的…

从GPT到chatGPT(一):GPT1

GPT1 文章目录 GPT1前言正文模型架构无监督学习有监督学习处理不同特定任务 实验训练细节实验结果 分析预训练层参数转移的影响zero-shot的表现消融实验 总结 前言 GPT1&#xff0c;出自于OpenAI的论文《Improving Language Understanding by Generative Pre-Training》&#…

ChatGPT+MindShow快速制作ppt

一、ChatGPT&MindShow简介 1、什么是ChatGPT? ChatGPT是一种基于自然语言处理和深度学习技术的人工智能语言模型&#xff0c;使得人们可以更加方便地与计算机进行交互&#xff0c;如智能问答等。 2、什么是MindShow? MindShow只需要在网页上登录即可&#xff0c;可以…

玩转ChatGPT:回答审稿人问题

一、写在前面 前段时间一篇时间序列预测的文章返修&#xff0c;还挺幸运的&#xff0c;给了个小修。 不过问题也问得有点刁钻&#xff0c;应该是个行家。 想到手头有小Chat&#xff0c;打算使用TA来辅助我回答审稿人问题。 以下展示仅仅提供一个工作流和思路&#xff0c;具体…

Jina AI 创始人肖涵博士:揭秘 Auto-GPT 喧嚣背后的残酷真相

Auto-GPT 究竟是一个开创性的项目&#xff0c;还是一个被过度炒作的 AI 实验&#xff1f;本文为我们揭开了喧嚣背后的真相&#xff0c;并揭示了 Auto-GPT 不适合实际应用的生产局限性。 背景介绍 这两天&#xff0c;Auto-GPT&#xff0c;一款让最强语言模型 GPT-4 能够自主完成…

两款吾爱破解优秀软件,批量查找文本,图像视频画质增强

批量查找文本 By&#xff1a;tuao 我们在电脑中查找文件的方式有很多&#xff0c;只要知道文件名便能很容易找到 但如果只记得文档中的某个关键词&#xff0c;而忘记文件名称的话&#xff0c;找起来就有些费劲了 这款工具便可以批量的在word、wps、excel、pdf和txt中查找文本…

吾爱破解论坛2021年11月11日,光棍节免费开放注册

点击上方蓝字"优派编程"选择“加为星标”&#xff0c;第一时间关注原创干货 官方原话&#xff1a; 吾爱破解论坛从2008年3月13日建立以来&#xff0c;陪伴众多坛友走过了12年艰辛而辉煌的风雨历程&#xff0c;以带领新手走入密界大门为基础&#xff0c;汇集了一大批爱…

吾爱出品,必属精品

前言 吾爱破解论坛是一个非常老牌的软件技术交流地&#xff0c;虽然经过多次整改&#xff0c;人气不如从前了 但也依旧能找到很多好玩好用的东西&#xff0c;小编不少分享的软件都是在这个论坛找到的 今天又收集了4款吾爱上高评霸榜的小工具&#xff0c;都很实用&#xff01…

txt工具吾爱版

每次在网上复制的文本内容都是乱七八糟的&#xff1f;那么可以配合txt工具来处理&#xff0c;这是由吾爱破解pgzzh用户出品的一款非常实用、绿色小巧的电脑排版工具&#xff0c;不要看该软件大小才几百KB&#xff0c;其功能是非常好用的&#xff0c;主要就是为用户们提供了去除…

吾爱studio3T

根本逻辑讲解&#xff1a;通过注册表更改studio3T试用时间到期的两种方 法 本例逻辑为通过不断重置studio 3t的试用时间达成伪永久&#xff0c;此软件少有永久免费版&#xff0c;如有永久的请在评论区我。 第一种方法 第一步&#xff1a;winr输入 regedit打开注册表 第二步&…

吾爱第二课-去除网页弹窗

目录 WindowsAPI实例1实例2修改主页内置广告1 用到的工具RestoratorFix ResourceProcexpProcmon WindowsAPI API函数提供应用程序所需要的窗口管理、图形设备接口、内存管理等服务功能。这些功能以函数库的形式组织在一起&#xff0c;形成了Windows应用程序编程接口。 A代表A…