关于mysql排序

关于mysql排序,第1张

在执行查询结果时,默认情况下查询结果无序排列。但我们有时需要对数据按一定规则进行排序。这时可以通过ORDER BY子句来实现这个功能。语法如下:

SELECT <*,column [alias],...> FROM table

[WHERE condition(s)]

[ORDER BY column[ASC|DESC]];

默认是ASC指定的升序排列,DESC用来指定降序排列。

1、升序排序:

使用ORDER BY子句时,默认情况下数据是按升序排列的,故可以用ASC关键字指点升序排列,或者不指定,默认就是升序,显示效果是一样的,如下图:

2、降序排序:

当需要查询结果降序排列时,必须在排序后指定DESC关键字。如下图是查看职员薪水的降序排列:

InnoDB在创建或重建索引时执行批量加载,而不是一次插入一个索引记录。这种索引创建方法也称为排序索引构建。空间索引不支持排序索引构建。

索引构建分为三个阶段。在第一阶段, 扫描聚集索引,生成索引条目并添加到排序缓冲区。当排序缓冲区变满时,条目将被排序并写入临时中间文件。此过程也称为 “运行”。在第二阶段,将一个或多个运行写入临时中间文件,对文件中的所有条目执行合并排序。在第三个也是最后一个阶段,排序后的条目被插入到 B-tree中。

在引入排序索引构建之前,使用插入 API 将索引条目一次插入 B 树中的一条记录。此方法涉及打开 B 树 游标以查找插入位置,然后使用 乐观插入将条目插入 B 树页面。如果由于页面已满而导致插入失败, 则将执行悲观插入,这涉及打开 B-tree 游标并根据需要拆分和合并 B-tree 节点以找到条目空间。这种“自上而下”的弊端建立索引的方法是搜索插入位置的成本以及 B 树节点的不断拆分和合并。

排序索引构建使用“自下而上”建立索引的方法。使用这种方法,对最右侧叶页的引用保存在 B 树的所有级别。分配必要 B 树深度的最右侧叶页,并根据其排序顺序插入条目。一旦叶页已满,就会将节点指针附加到父页,并为下一次插入分配一个兄弟叶页。这个过程一直持续到所有条目都被插入,这可能导致插入到根级别。分配同级页时,释放对先前固定叶页的引用,新分配的叶页成为最右边的叶页和新的默认插入位置。

要为将来的索引增长留出空间,您可以使用innodb_fill_factor变量来保留一定百分比的 B 树页面空间。例如,设置 innodb_fill_factor为 80 会在排序索引构建期间保留 B 树页面中 20% 的空间。此设置适用于 B 树的叶子页面和非叶子页面。它不适用于用于 TEXT或 BLOB条目的外部页面。保留的空间量可能与配置不完全相同,因为innodb_fill_factor值被解释为提示而不是硬限制。

全文索引支持排序索引构建 。以前,SQL 用于将条目插入全文索引。

对于压缩表,以前的索引创建方法将条目附加到压缩页和未压缩页。当修改日志(表示压缩页面上的可用空间)变满时,将重新压缩压缩页面。如果由于空间不足而导致压缩失败,则页面将被拆分。使用排序索引构建,条目仅附加到未压缩的页面。当一个未压缩的页面变满时,它就会被压缩。自适应填充用于确保在大多数情况下压缩成功,但如果压缩失败,则会拆分页面并再次尝试压缩。这个过程一直持续到压缩成功。

在排序索引构建期间禁用重做日志记录。相反,有一个 检查点来确保索引构建可以承受意外退出或失败。检查点强制将所有脏页写入磁盘。在排序索引构建期间,页面清理线程会定期收到信号以刷新 脏页,以确保可以快速处理检查点 *** 作。通常,当干净页面的数量低于设置的阈值时,页面清理线程会刷新脏页面。对于排序索引构建,脏页会被及时刷新以减少检查点开销并行化 I/O 和 CPU 活动。

排序索引构建可能会导致 优化器统计信息与以前的索引创建方法生成的统计信息不同。统计数据差异是由于用于填充索引的算法不同造成的。

由于历史原因,MySQL刚开始设计的时候,"天真的"认为使用3个字节就足够存储字符串了,因此将UTF-8进行阉割然而遇到复杂的汉字或者emoji表情等4字节的宽字符的时候,存储就会出现异常,因此在版本5.7.3开始引入utf8mb4,其表示为most bytes 4,即最多占用4个字节。

utf8mb4_unicode_ci是基于官方的Unicode规则进行排序和压缩,其算法相对负责,对于大部分的语言和字符集排序有着很高的准确率而uft8mb4_general_ci可以理解为一种为了提升速度的简化版Unicode规则,但由于它不完全遵循Unicode规则,在使用某种特定语言或者字符集时,会出现非预期的结果。

例:

总结:

UTF-8编码的字符可以是1-4个字节,但是在MySQL中最大只能存储3个字节。

在版本5.5开始引入innodb_large_prefix,其默认值为off,索引的前缀最大限制为767个字节;若值为on时(版本5.7.7开始作为默认值),最大限制为3072个字节。

总结:

在后期版本 innodb_large_prefix 将会被逐渐废弃并移除。从版本8.0开始,索引长度限制由表字段(row format)决定,若为DYNAMIC或COMPRESSED时,限制值为3072;为REDUNDANT或COMPACT时,限制值为767。且row_format=dynamic时,长度3072是基于innodb_page_size=16KB,随着innodb_page_size的值按比例增减,其索引前缀长度也响应减小,如若为8KB时,长度为1536,因此在限制索引长度时,需根据使用的MySQL版本以及相应的参数进行配置决定。


欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/zaji/7459018.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2023-04-05
下一篇 2023-04-05

发表评论

登录后才能评论

评论列表(0条)

保存