数据库
首页 > 数据库> > mysql – 排序和分页

mysql – 排序和分页

作者:互联网

我在我的数据库mysql中有一千条记录,我使用分页来检索10个结果.

当我在我的查询中添加订单时,它会减慢但是当我省略它时,查询运行得非常快.

我知道问题来自查询加载整个结果,对它们进行排序,然后它获得10条记录.

我不使用索引,因为订单的列使用是PK,我认为如果我在mysql中没有错,则会在每个主键上自动创建索引

>为什么我的PK上的索引是我订购的列.
不曾用过 ?
>有没有其他替代方案可以在不加载所有数据的情况下执行排序?
>如何在表的第一行而不是表的末尾添加新插入的数据?

我的SQL查询

    select distinct ...... order by appeloffre0_.ID_APPEL_OFFRE desc limit 10

和我的索引

mysql> show index from appel_offre;
+-------------+------------+--------------------+--------------+---------------------+-----------+-------------+----------+--------+------+------------+---------+---------------+
| Table       | Non_unique | Key_name           | Seq_in_index | Column_name         | Collation | Cardinality | Sub_part | Packed | Null | Index_type | Comment | Index_comment |
+-------------+------------+--------------------+--------------+---------------------+-----------+-------------+----------+--------+------+------------+---------+---------------+
| appel_offre |          0 | PRIMARY            |            1 | ID_APPEL_OFFRE      | A         |       13691 |     NULL | NULL   |      | BTREE      |         |               |
| appel_offre |          1 | appel_offre_ibfk_1 |            1 | ID_APPEL_OFFRE_MERE | A         |           2 |     NULL | NULL   | YES  | BTREE      |         |               |
| appel_offre |          1 | appel_offre_ibfk_2 |            1 | ID_ACHETEUR         | A         |           2 |     NULL | NULL   |      | BTREE      |         |               |
| appel_offre |          1 | appel_offre_ibfk_3 |            1 | USER_SAISIE         | A         |           2 |     NULL | NULL   | YES  | BTREE      |         |               |
| appel_offre |          1 | appel_offre_ibfk_4 |            1 | USER_VALIDATION     | A         |           4 |     NULL | NULL   | YES  | BTREE      |         |               |
| appel_offre |          1 | ao_fk_3            |            1 | TYPE_MARCHE         | A         |           2 |     NULL | NULL   | YES  | BTREE      |         |               |
| appel_offre |          1 | ao_fk_5            |            1 | USER_CONTROLE       | A         |           2 |     NULL | NULL   | YES  | BTREE      |         |               |
+-------------+------------+--------------------+--------------+---------------------+-----------+-------------+----------+--------+------+------------+---------+---------------+
7 rows in set (0.03 sec)

在explain cmd中没有选择索引:

+----+-------------+---------------+--------+-------------------------------------+--------------------+---------+----------------
| id | select_type | table         | type   | possible_keys                       | key                | key_len | ref
+----+-------------+---------------+--------+-------------------------------------+--------------------+---------+----------------
|  1 | SIMPLE      | appeloffre0_  | ALL    | NULL                                | NULL               | NULL    | NULL

更新解决方案

问题来自于我删除它时查询最终使用索引.

解决方法:

因为您已经在“USER_VALIDATION”上使用索引,所以MySQL不会使用ID索引.

尝试重建USER_VALIDATION索引以包含ID:

CREATE UNIQUE INDEX appel_offre_ibfk_4 ON appel_offre (USER_VALIDATION, ID);

更新

记录所有Hibernate查询,提取慢查询并在db控制台中使用EXPLAIN,以了解MySQL为此查询选择的执行计划.即使有索引,db也可能使用FULL TABLE SCAN,因为索引太大而无法容纳到内存中.尝试给它一个提示,如in this post所述.

根据MySQL ORDER BY optimization documentation你应该:

要提高ORDER BY速度,请检查是否可以让MySQL使用索引而不是额外的排序阶段.如果无法做到这一点,您可以尝试以下策略:

• Increase the sort_buffer_size variable value.

• Increase the read_rnd_buffer_size variable value.

• Use less RAM per row by declaring columns only as large as they need
to be to hold the values stored in them. For example, CHAR(16) is
better than CHAR(200) if values never exceed 16 characters.

• Change the tmpdir system variable to point to a dedicated file
system with large amounts of free space. The variable value can list
several paths that are used in round-robin fashion; you can use this
feature to spread the load across several directories. Paths should be
separated by colon characters (“:”) on Unix and semicolon characters
(“;”) on Windows, NetWare, and OS/2. The paths should name directories
in file systems located on different physical disks, not different
partitions on the same disk.

还要确保DISTINCT不会否决您的索引.尝试删除它,看看它是否有帮助.

标签:querydsl,sql,mysql,spring-data,hibernate
来源: https://codeday.me/bug/20190830/1766654.html