您期望特定顺序的所有查询都应该包含 ORDER BY 子句吗?

Han*_*non 3 sql-server order-by

为了更好地理解 SQL Server 查询处理器,我一直在思考ORDER BY子句是如何工作的,以及 SQL Server 如何提供结果。

对于任何给定的数据集,SQL Server 似乎将以完全相同的顺序提供结果,这些数据集保持不变并且永远不会改变。一旦您引入任何类型的不确定性,例如开发人员更改某些内容,就不能再期望结果的顺序是相同的。

简单地以相同的顺序查看结果,每次按下F5并不能保证您期望的结果。

尝试这个:

USE TempDB;
DROP TABLE TestOrderBy;
DROP TABLE TestOrderBy2;
CREATE TABLE TestOrderBy
(
    ID INT NOT NULL CONSTRAINT PK_TestOrderBy PRIMARY KEY CLUSTERED IDENTITY(1,1)
    , SomeData varchar(255)
);
INSERT INTO TestOrderBy (SomeData) VALUES ('E');
INSERT INTO TestOrderBy (SomeData) VALUES ('D');
INSERT INTO TestOrderBy (SomeData) VALUES ('C');
INSERT INTO TestOrderBy (SomeData) VALUES ('B');
INSERT INTO TestOrderBy (SomeData) VALUES ('A');

CREATE TABLE TestOrderBy2
(
    ID INT NOT NULL CONSTRAINT PK_TestOrderBy2 PRIMARY KEY CLUSTERED IDENTITY(1,1)
    , SomeData varchar(255)
);
INSERT INTO TestOrderBy2 (SomeData) VALUES ('E');
INSERT INTO TestOrderBy2 (SomeData) VALUES ('D');
INSERT INTO TestOrderBy2 (SomeData) VALUES ('C');
INSERT INTO TestOrderBy2 (SomeData) VALUES ('B');
INSERT INTO TestOrderBy2 (SomeData) VALUES ('A');

SELECT SomeData 
FROM TestOrderBy
UNION ALL
SELECT SomeData
FROM TestOrderBy2;

CREATE INDEX IX_TestOrderBy_SomeData ON TestOrderBy (SomeData);
CREATE INDEX IX_TestOrderBy2_SomeData ON TestOrderBy2 (SomeData);

SELECT SomeData 
FROM TestOrderBy
UNION ALL
SELECT SomeData
FROM TestOrderBy2;
Run Code Online (Sandbox Code Playgroud)

结果:

在此处输入图片说明

如您所见,在查询中选择的字段上添加一个简单的索引会改变结果的顺序。

从这里开始,ORDER BY除非我真的不在乎,否则我会添加。

Aar*_*and 9

我有一个更简单的重现:

CREATE TABLE #x(z CHAR(1));
CREATE TABLE #y(z CHAR(1));

INSERT #x SELECT 'O';
INSERT #x SELECT 'R';
INSERT #x SELECT 'D';

INSERT #y SELECT 'E';
INSERT #y SELECT 'R';

SELECT z FROM #x
UNION ALL 
SELECT z FROM #y;
Run Code Online (Sandbox Code Playgroud)

结果:

O
R
D
E
R
Run Code Online (Sandbox Code Playgroud)

现在添加一个索引:

CREATE CLUSTERED INDEX z ON #x(z);

SELECT z FROM #x
UNION ALL 
SELECT z FROM #y;
Run Code Online (Sandbox Code Playgroud)

结果:

D -|
O -|- ordered based on the clustered index, not how originally inserted
R -|
E
R
Run Code Online (Sandbox Code Playgroud)

这仍然会产生 #x 的前三行和 #y 的后两行,所以仍然不能证明 SQL Server 可能以与查询中物理布局不同的顺序返回这些整个查询(只是你可以t 依赖于这些集合内的排序)。但显然,这种神话般的“遵守命令一次,它将永远为真”的说法需要被扼杀。

底线:不要依赖观察到的顺序。如果您想要某种排序,请使用 ORDER BY 说出来。

另外,请阅读 SQL 团队中非常聪明的人 Conor Cunningham 的这篇文章