如果我有一些UNION声明作为一个人为的例子:
SELECT * FROM xxx WHERE z = 1
UNION
SELECT * FROM xxx WHERE z = 2
UNION
SELECT * FROM xxx WHERE z = 3
What is the default order by behaviour?
我看到的测试数据基本上不会按照上面指定的顺序返回数据 . 即数据是有序的,但我想知道这有什么优先规则 .
另一件事是,在这种情况下,xxx是一个视图 . 视图将3个不同的表连接在一起以返回我想要的结果 .
7 回答
没有默认订单 .
没有 Order By 子句,返回的顺序是未定义的 . 这意味着SQL Server可以按照自己喜欢的顺序将它们带回来 .
编辑:根据我所看到的,没有Order By,结果返回的顺序取决于查询计划 . 因此,如果有一个正在使用的索引,结果可能会按此顺序返回,但再次无法保证 .
关于添加ORDER BY子句:
这对大多数人来说可能是基本的,但我想我加上这个 . 有时您不希望结果混合,因此您需要第一个查询的结果,然后是第二个,依此类推 . 要做到这一点,我只需添加一个虚拟的第一列并按顺序排序 . 由于忘记在联合中对列进行别名可能存在问题,我通常在order by子句中使用序数,而不是列名 .
例如:
当我要运行两个查询并且我知道只有一个将返回任何结果时,虚拟序列列也很有用 . 然后我可以检查返回结果的序数 . 这使我不必进行多个数据库调用和大多数空结果集检查 .
刚刚找到了实际答案 .
因为UNION删除了重复项,所以它会执行DISTINCT SORT . 这是在连接所有UNION语句之前完成的(检查执行计划) .
要停止排序,请执行UNION ALL,这也不会删除重复项 .
If you care what order the records are returned, you MUST use an order by.
如果将其遗漏,它可能看起来有条理(基于查询计划选择的索引),但您今天看到的结果可能不是您期望的结果,甚至可能在明天运行相同查询时更改 .
编辑:一些好的,具体的例子:(所有的例子都是MS SQL服务器)
Conor Cunningham显示了表变大时表观顺序如何变化(如果查询优化器决定使用并行执行计划) .
Hugo Kornelis证明明显的顺序是 not 始终基于主键 . Here is his follow-up post有解释 .
UNION在结果集排序方面可能具有欺骗性,因为数据库有时会使用排序方法来提供UNION中隐含的DISTINCT,这使得它看起来像是故意排序的行 - 这不适用于UNION ALL当然,没有明显的区别 .
但是,有一些隐式不同的算法,例如10g中的Oracle哈希方法,不会对其应用任何排序 .
正如DJ所说,总是使用ORDER BY
很常见的是遇到写得不好的代码,假设表数据是按插入顺序返回的,并且编码器有95%的时间使用它并且从来没有意识到这是一个问题,就像许多常见的数据库一样(MSSQL,Oracle, MySQL的) . 它当然是一个完整的谬误,应该在遇到时始终予以纠正,并且无一例外地自己使用Order By子句 .
根据我的实际经验,您可以使用“UNION”对“UNION ALL”更改顺序...即如果您的查询是这样的
您可以通过将“UNION”替换为“UNION ALL”来翻转顺序...然后结果将是