草庐IT

留给CBO优化器的弯道不多了

白鳝 2023-03-28 原文
​前几天一个做数据库产品的朋友和我聊起在国产数据库上的弯道超车问题,他觉得对于通用关系型数据库,Oracle已经领先太多了,如果不弯道超车,国产数据库永远没有机会赶上Oracle。弯道超车一直被很多朋友看作是超越的捷径,不过我认为弯道超车一定是以实力作为后盾才能够完成的。要想弯道超车,后车的引擎必须高于前车,至少是二者相当,没有实力做保障,弯道技术再好,也是很难完成超车的。

在通用关系型数据库领域,想要对Oracle实现弯道超车,大家都会选择CBO优化器。AI4DB是被大家寄予厚望的。通过AI算法的辅助来纠正执行计划中的错误,或者帮助某条SQL选择一个更好的执行计划。其主要方法是基于历史数据的分析,通过一定的参数(比如表分析数据、历史执行计划的效率等),通过算法计算执行计划的成本,在重大决策中辅助CBO的规则引擎,比如当HASH JOIN和NESTED LOOP经常会选错的时候,通过AI算法辅助,让CBO选择的执行计划更为准确。

实际上Oracle这些年也一直CBO上发力,动态CURSOR是Oracle用于解决这个问题的方法,当SQL在执行过程中发现NESTED LOOP成本过高的时候,自动将目前的执行暂停,更换为HASH JOIN,从而避免某些SQL出现严重的性能问题。只不过Oracle目前的算法还不够完善,因此动态CURSOR有时候还会出错。

Oracle的CBO优化器是基于数据模型的优选算法的,其主要方法是通过各种统计数据,对某个SQL的不同算子计算成本,最后将一条SQL的各种执行方式的成本都算完后,选择其中成本最低的执行计划去执行。这种方法也是目前绝大多数数据库系统分析执行计划的基础算法。到目前的版本为止,Oracle并没有选择通过AI算法来获得执行计划,而是继续沿用其传统的算法。不过随着Oracle的数十年的发展,其CBO优化器的核心算法基础上,已经积累了大量的补丁,这些补丁都是对核心主算法的纠正,在Oracle内部被称为FIX。每个FIX实际上就是一个特殊场景下SQL选择执行计划中的修正模型,都是在实战中遇到问题后,标准CBO算法无法解决问题时的一种特殊处理,也可以称为经验模型。此外,Oracle还将其中的一些特别重要的修正进行了特殊的处理,设置了一些隐含参数加以控制。这些修正往往不是CBO优化器的不足,而是在不同的应用场景中,特殊的用户数据与用户硬件环境可能导致CBO优化器产生错误的选择,通过这些参数可以加以调整。其中最为著名的莫过于optimizer_index_cost_adj,这个参数可以调整CBO优化器在计算索引扫描时的成本,在二十年前的Oracle 8i/9i时代,我们经常通过调整这个参数来避免不必要的对全表扫描的错误选择,让数据库更倾向于使用索引扫描。

在Oracle 11.2.0.4中,CBO优化器的可调整参数有329个,FIX有846个。到了19.15.0.0版本,CBO优化器可调整参数的数量高达612个,FIX的数量达到了1369个。实际上每个FIX后面都有无数个用户的痛苦经历,是Oracle数据库的CBO优化器在用户环境中遇到了问题后的修正。

Oracle数据库的优化器是十分优秀的,这一点大家都是公认的,但是其优秀的优化器依然无法解决所有的用户的问题,依然需要不断的通过添加参数来做更精细的控制,甚至加入某些特殊的修正来解决问题。

目前我们国产数据库的优化器恐怕还在重点完善CBO优化器的核心算法,还没有遇到过如此多的实战案例,发现那么多主逻辑可能存在的问题。这些参数与FIX必须是在大量的实战中获得的,因此有些国产数据库厂家想另辟蹊径了。通过AI4DB是不是可以绕开这个问题,实现在CBO上的弯道超车呢?恐怕有此想法的朋友要失望了,CBO优化器是基于统计数据与算法规则的,历史的SQL执行情况可以提供参考,但是无法作为下一次解析SQL时的可靠依据。因为数据在不断的变化,参数也在变化,而CBO优化器的每次解析,都决定了SQL语句是否能够合理的执行。一次错误的解析很可能引发一场灾难。因此AI算法在这个场景中可以起到辅助发现SQL问题的作用,但是无法替代规则来生成执行计划。我们的CBO优化器也只能在实战中不断的经受挑战,不断的经历痛苦的折腾,才能变得越来越强大。当我们的优化器的FIX和可调整参数能够达到Oracle的时候,才真正算是成熟了。CBO优化器成长的最佳途径是在实战中不断完善,而不是凭着我们的研发人员的想象力,在家里闭门造车。

先不要空谈弯道超车,扎扎实实的在用户厂家中去修炼,把优化器一点点做好吧,实际上在现阶段,能够先远远的跟上最先进的数据库产品,已经是国产数据库的成功了。

有关留给CBO优化器的弯道不多了的更多相关文章

  1. Ruby 缺少常量表达式优化? - 2

    我希望Ruby的解析器会进行这种微不足道的优化,但似乎并没有(谈到YARV实现,Ruby1.9.x、2.0.0):require'benchmark'deffib1a,b=0,1whileb由于这两种方法除了在第二种方法中使用预定义常量而不是常量表达式外是相同的,因此Ruby解释器似乎在每个循环中一次又一次地计算幂常数。是否有一些Material说明为什么Ruby根本不进行这种基本优化或只在某些特定情况下进行? 最佳答案 很抱歉给出了另一个答案,但我不想删除或编辑我之前的答案,因为它下面有有趣的讨论。正如JörgWMittag所说,

  2. ruby-on-rails - 优化读取数据库和写入csv文件 - 2

    我正在尝试从数据库中读取大量单元格(超过100.000个)并将它们写入VPSUbuntu服务器上的csv文件。碰巧服务器没有足够的内存。我正在考虑一次读取5000行并将它们写入文件,然后再读取5000行,等等。我应该如何重构我当前的代码以使内存不会被完全消耗?这是我的代码:defwrite_rows(emails)File.open(file_path,"w+")do|f|f该函数由sidekiqworker调用:write_rows(user.emails)感谢您的帮助! 最佳答案 这里的问题是,当您调用emails.each时,

  3. 软约束、硬约束、Minimum Snap的轨迹优化方法 - 2

    文章目录前言约束硬约束的轨迹优化Corridor-BasedTrajectoryOptimizationBezierCurveOptimizationOtherOptions软约束的轨迹优化Distance-BasedTrajectoryOptimization优化方法前言可以看看我的这几篇Blog1,Blog2,Blog3。上次基于MinimumSnap的轨迹生成,有许多优点,比如:轨迹让机器人可以在某个时间点抵达某个航点。任何一个时刻,都能数学上求出期望的机器人的位置、速度、加速度、导数。MinimumSnap可以把问题转换为凸优化问题。缺点:MnimumSnap可以控制轨迹一定经过中间的

  4. ruby-on-rails - 负载测试期间 Unicorn CPU 使用率激增,优化方法 - 2

    我对为我的RubyonRails3.1.3应用优化我的Unicorn设置的方法很感兴趣。我目前正在高CPU超大实例上生成14个工作进程,因为我的应用程序在负载测试期间似乎受CPU限制。在模拟负载测试中,每秒大约20个请求重放请求,我的实例上的所有8个内核都达到峰值,盒子负载飙升至7-8个。每个unicorn实例使用大约56-60%的CPU。我很好奇可以通过哪些方式对其进行优化?我希望能够每秒将更多请求汇集到这种大小的实例上。内存和所有其他I/O一样完全正常。在我的测试过程中,CPU越来越低。 最佳答案 如果您受CPU限制,您希望使用

  5. 美团外卖搜索基于Elasticsearch的优化实践 - 2

    美团外卖搜索工程团队在Elasticsearch的优化实践中,基于Location-BasedService(LBS)业务场景对Elasticsearch的查询性能进行优化。该优化基于Run-LengthEncoding(RLE)设计了一款高效的倒排索引结构,使检索耗时(TP99)降低了84%。本文从问题分析、技术选型、优化方案等方面进行阐述,并给出最终灰度验证的结论。1.前言最近十年,Elasticsearch已经成为了最受欢迎的开源检索引擎,其作为离线数仓、近线检索、B端检索的经典基建,已沉淀了大量的实践案例及优化总结。然而在高并发、高可用、大数据量的C端场景,目前可参考的资料并不多。因此

  6. ruby - 哪个是 ANTLR 在 ruby​​ 中创建解析器的最佳对应物? - 2

    我使用antlr和javacc/freecc有一段时间了。现在我需要使用antlr语法编写一堆解析器,但此类解析器需要用ruby​​lang编写。我用谷歌搜索但没有找到。是否有任何采用antlr语法并创建解析器的ruby​​解析器生成器?如果有很多,您认为哪个是最好的?TIA保罗 最佳答案 您可以使用JRuby轻松逃脱并将您的ANTLR解析器保存在java中。如果PEGs足以胜任你的工作,treetop和更新的citrus是ruby​​ists使用的常用工具。我在研究项目时挖掘的其他解析器是:peggy,Kanocc,Racc.对于

  7. ruby - Ruby <=> 组合器的实现 - 2

    并不少见,有人想实现(比较,或“宇宙飞船”)产品数据类型的运算符,即具有多个字段的类(所有这些(我们希望!)已经实现了),按特定顺序比较字段。def(o)f1o.f1&&(return1)f2o.f2&&(return1)return0end这既乏味又容易出错,尤其是对于很多字段。它很容易出错,以至于我经常觉得我应该对该函数进行单元测试,这只会增加乏味和冗长。Haskell提供了一种特别好的方法来做到这一点:importData.Monoid(mappend)importData.Ord(comparing)--Fromthestandardlibrary:--dataOrdering

  8. 基于RTS超低延时直播优化强互动场景体验 - 2

    RTS在阿里云视频直播的基础上进行底层技术优化,通过集成阿里云播放器SDK,支持在千万级并发场景下节点间毫秒级延时直播的能力,弥补了传统直播存在3~6秒延时的问题,确保了超低延时、低卡顿、秒开流畅的直播观看体验。本文介绍了基于RTS超低延迟直播优化强互动场景体验的最佳实践方案,并以阿里云播放器Aliplayer为例,详细介绍RTS超低延迟拉流接入、自动降级、排障信息获取等逻辑的实现,助力企业打造互动直播行业的产品竞争力。适用场景该方案适用于对超低延迟直播有诉求的客户,尤其是业务中存在强互动场景直播的场景。强互动场景直播主要是指对主播和观众存在互动,或观众存在更高实时性观看、画面互动需求的情况,

  9. ruby - 无法使用 CONSTANT 优化字符串 - 2

    我目前正在研究Ruby2.1.1的改进,但遇到了一些奇怪的事情。我正在尝试改进String类并定义一个名为FOO的常量。沙箱.rbmoduleFoobarrefineStringdoFOO="BAR"deffoobar"foobar"endendendusingFoobarputs"".class::FOO#=>uninitializedconstantString::FOO(NameError)puts"".foobar#=>"foobar"这给了我未初始化的常量String::FOO(NameError)。但是我可以调用"".foobar这让我相信我在正确的范围内。奇怪的是,如果我

  10. ruby - 如何使用 SASS 解析 .scss 文件中所有 CSS 选择器的列表? - 2

    我想以编程方式解析.scss文件以生成该文件中使用的选择器的平面列表,主要作为某些静态代码分析的基础。在SASS术语中,我正在寻找一种方法来获取给定.scss文件的所有Sass::Tree::RuleNode的列表。到目前为止,我正在使用Sass::Engine.for_file创建树。然后,根据文档,为了在各个节点上使用Sass::Tree::RuleNode.resolved_rules,我必须使用Tree::Visitors::Cssize。但是某处有一个(可能很简单的)错误。require'sass'sass_engine=Sass::Engine.for_file('file

随机推荐