我的测试服务器版本如下:
MySQL Server 5.7.20
MariaDB Server 10.1.9
我在两个数据库中制作了相同的表格。
CREATE TABLE `sort_test` (
`ind` int(11) NOT NULL AUTO_INCREMENT,
`time` datetime DEFAULT CURRENT_TIMESTAMP,
PRIMARY KEY (`ind`)
) ENGINE=InnoDB;
我在两张表中插入了九条记录
insert sort_test(time) values(now());
insert sort_test(time) values(now());
insert sort_test(time) values(now());
...
insert sort_test(time) values(now());
当我执行SELECT * FROM sort_test order by time desc;
时,结果彼此相等。
+-----+---------------------+
| ind | time |
+-----+---------------------+
| 9 | 2018-01-05 23:43:59 |
| 8 | 2018-01-05 23:43:58 |
| 7 | 2018-01-05 23:43:57 |
| 6 | 2018-01-05 23:43:56 |
| 5 | 2018-01-05 23:43:55 |
| 4 | 2018-01-05 23:43:54 |
| 3 | 2018-01-05 23:43:53 |
| 2 | 2018-01-05 23:43:52 |
| 1 | 2018-01-05 23:43:51 |
+-----+---------------------+
9 rows in set (0.01 sec)
顺便说一下,当我执行select * from (SELECT * FROM sort_test order by time desc) as A;
时,结果是不同的。
mariadb> select * from (SELECT * FROM sort_test order by time desc) as A;
+-----+---------------------+
| ind | time |
+-----+---------------------+
| 1 | 2018-01-05 23:43:51 |
| 2 | 2018-01-05 23:43:52 |
| 3 | 2018-01-05 23:43:53 |
| 4 | 2018-01-05 23:43:54 |
| 5 | 2018-01-05 23:43:55 |
| 6 | 2018-01-05 23:43:56 |
| 7 | 2018-01-05 23:43:57 |
| 8 | 2018-01-05 23:43:58 |
| 9 | 2018-01-05 23:43:59 |
+-----+---------------------+
9 rows in set (0.02 sec)
与
mysql> select * from (SELECT * FROM `sort_test` order by time desc) as A;
+-----+---------------------+
| ind | time |
+-----+---------------------+
| 9 | 2018-01-05 23:43:59 |
| 8 | 2018-01-05 23:43:58 |
| 7 | 2018-01-05 23:43:57 |
| 6 | 2018-01-05 23:43:56 |
| 5 | 2018-01-05 23:43:55 |
| 4 | 2018-01-05 23:43:54 |
| 3 | 2018-01-05 23:43:53 |
| 2 | 2018-01-05 23:43:52 |
| 1 | 2018-01-05 23:43:51 |
+-----+---------------------+
9 rows in set (0.10 sec)`
结果按不同顺序排序。
为什么呢?发生了什么事?
答案 0 :(得分:1)
如果没有ORDER BY
,则无法保证结果的顺序。外部ORDER BY
上没有SELECT
。子查询提供无序集合或行。也就是说,优化器可以自由忽略子查询中的ORDER BY
。
优化程序是否具有此自由取决于您正在查看哪个MySQL版本的哪个版本。也许它还取决于月相。
如何使结果相同?那么,为什么? SELECT * FROM ( subquery );
是不必要的 - 只需运行子查询即可。好的,也许你正在做一些你从查询中简化出来的东西?如果是这样,请将其重新放入,以便我们讨论 。
几年前,当“groupwise max”代码无法在某些版本上运行时,我被烧毁了。
好的,有一个kludge可以在不久的将来做你想要的事情:在子查询中添加一个带有大号的LIMIT
。 未完善!
我和Mark在一起 - 你的期望是错误的。