美文网首页
mysql Order By所引发的

mysql Order By所引发的

作者: lionel880 | 来源:发表于2019-01-22 15:21 被阅读0次

    生产接到公司运营的反馈,部分数据丢失,由于程序已经稳定运行了1年多,没想到sql语句还隐藏着坑。
    问题的定位和复现目前都很清楚了,别人的文章也写得很清楚,我这就是简单在整理一下思路

    参考文章:
    MySQL使用order by + limit语句的坑
    MySQL排序内部原理探秘
    外部排序

    1、问题的表现

    数据的刷入有缺失,但程序无报错。最终怀疑是sql查询的时候数据本身有缺失。
    sql 排序后,每次取一部分数据,但排序字段为跟新时间,此字段并没有添加索引

    select * from tbl order by  upd_ts limit n offset m
    

    每次都不断的增加offset

    2、基础知识储备

    2.1外部排序

    关于外部排序,可以参考外部排除的参考文献,了解外部排序的基本方法

    • 基础方案
      外部排序,之所以需要是因为数据的规模超过了内存的限制。所以基础的思路是通过分而治之的思路,将数据进行先拆分,在归并排序。
      最基础的就是方案:快排+归并
    • 优化
      这个基础上,优化总的思路就一个,减少归并的次数
      减少归并的次数方法:
      1.每一个段分大一点:通过小根堆置换选择排序生成段
      这个扫雪机模型理解了很多,才理解为什么平均为2倍,有空得专门写一篇
      2.相同的段数合并次数减少:多路归并
    2.2 mysql的排序

    mysql的排序会在order by,group by 等语法中被使用,其中limit的大小也会影响算法,详细可以看参考文献的《[MySQL排序内部原理探秘》

    • 排序字段如果是索引
      事情就会很少,只需要根据 B-tree找到第一个,然后依次去过去就行。特别注意,就算是使用索引字段进行排序,也不意味着真的就使用了索引,可以通过 explain进行分析。mysql内部会优化,当字段过长时,可能会是全表扫描排序更快,这个要注意,有参数进行调节
    • 排序字段如果是不是
      大致思路就是先找出结果,再排序,再选出相应数量limit返回

    mysql 的排序重复值的随机性来源有很多,由于没有了解源码,只能做猜测性分析
    1.快排的不稳定性
    2.limit导致的优先级队列优化,内部堆排序的不稳定性

    相关文章

      网友评论

          本文标题:mysql Order By所引发的

          本文链接:https://www.haomeiwen.com/subject/snpedqtx.html