sql-server-2008 – sql server如何排序数据?

前端之家收集整理的这篇文章主要介绍了sql-server-2008 – sql server如何排序数据?前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
我想知道sql server如何排序它的数据.
我注意到,如果我有一个不包含列“Id”的表,并且您选择数据没有“ORDER BY”sql server不会自动排序在主列上.

有没有人知道什么规则sql server跟随来排序它的数据?

解决方法

虽然很高兴想知道如何解释您经常看到相同的顺序,但我想指出,依靠底层数据库引擎的特定实现导致的隐式顺序绝对不是一个好主意.换句话说,它很高兴知道为什么,但你永远不应该依赖它.对于MS sql,唯一可靠地以特定顺序递送行的是一个明确的ORDER BY子句.

不同的RDMBS-es行为不同,一个特定的实例可能由于更新(补丁)而有所不同.不仅如此,即使RDBMS软件的状态也可能产生影响:“温暖”数据库的行为与“冷”数据库的行为不同,小表的行为与大型表的行为不同.

即使你有关于实现的背景信息(例如:“有一个聚簇索引,因此很可能数据将通过聚簇索引的顺序返回”),总有一种可能性,有另外一种机制你不不知道会导致以不同的顺序返回行(ex1:“如果另一个会话刚刚执行了一个完整的表扫描,结果集中的显式ORDER可能已被缓存,则后续的全面扫描将尝试将行从缓存“; ex2:”可以通过对数据进行排序来实现GROUP BY,从而影响行的返回顺序“; ex3:”如果选定的列都在已经缓存在内存中的辅助索引中,引擎可以扫描辅助索引而不是表,最有可能按次序索引的顺序返回行“).

这是一个非常简单的测试,说明了我的一些观点.

首先,启动sql Server(我正在使用2008).创建此表:

create table test_order (
    id int not null identity(1,1) primary key,name varchar(10) not null 
)

检查表并看到创建了一个聚簇索引以支持id列上的主键.例如,在sql server管理工作室中,您可以使用树视图并导航到表格下方的索引文件夹.你应该看到一个索引,名称如下:PK__test_ord__3213E83F03317E3D(集群)

用这个语句插入第一行:

insert into test_order(name)
select RAND()

通过重复此语句插入更多行16次:

insert into test_order(name)
select RAND()
from   test_order

您现在应该有65536行:

select COUNT(*) 
from   test_order

现在,选择所有行,而不使用顺序:

select *
from   test_order

很可能,结果将按主键的顺序返回(尽管不能保证).这是我得到的结果(这是按主键的顺序):

#      id    name
1      1     0.605831
2      2     0.517251
3      3     0.52326
.      .     .......
65536  65536 0.902214

(#不是列,而是结果中行的顺序位置)

现在,在名称列上创建一个辅助索引:

create index idx_name on test_order(name)

选择所有行,但仅检索名称列:

select name
from   test_order

最可能的结果将通过辅助索引idx_name的顺序返回,因为只能扫描索引才能解析查询(i.o.w. idx_name是覆盖索引).这是我得到的结果,这的确是按照名称的顺序.

#      name
1      0.0185732
2      0.0185732
.      .........
65536  0.981894

现在,再次选择所有列和所有行:

select * 
from test_order

这是我得到的结果:

#      id    name
1      17    0.0185732
2      18    0.0185732
3      19    0.0185732
...    ..    .........

正如你所看到的,与我们第一次运行这个查询完全不同. (它看起来像是由二级索引排序的行,但是我没有解释为什么这样).

无论如何,底线是 – 不要依赖隐含的顺序.您可以想到为什么可以观察到特定顺序的解释,但即使如此,您也不能总是预测它(如在后一种情况),而不需要对实现和运行时状态的深入了解.

猜你在找的MsSQL相关文章