先排序還是先取值
2024-07-21 02:11:32
供稿:網友
先排序還是先取值
題目: ms sqlserver和oracle中取出表中按照某字段排序的前n條記錄
這個題目看上去似乎那么簡單, 兩種數據庫都提供order by 子句. 問題應該能夠迎刃而解吧.
先試一下ms sqlserver是怎么做的:
use northwind;
create table testsort (id integer);
insert into testsort values (3);
insert into testsort values (1);
insert into testsort values (4);
insert into testsort values (2);
select * from testsort;
-----------------------------------------
id
-----------
3
1
4
2
(4 row(s) affected)
假設我們要取出按照id排序的前三條記錄:
select top 3 * from testsort order by id ;
-----------------------------------------
id
-----------
1
2
3
(3 row(s) affected)
很簡單,一句話就解決了.
再試一下oracle (這里用oracle9i)
sql> create table testsort ( id number);
table created.
sql> insert into testsort values (3);
1 row created.
sql> insert into testsort values (1);
1 row created.
sql> insert into testsort values (4);
1 row created.
sql> insert into testsort values (2);
1 row created.
sql> commit;
commit complete.
sql> select * from testsort;
id
----------
3
1
4
2
oracle沒有ms sqlserver中取前n條記錄的top語法. 但是有rownum可以用來完成類似功能.
sql> select * from testsort where rownum <= 3 order by id;
id
----------
1
3
4
結果是不是有點出乎意料? 它并沒有返回所要求的 1 , 2 , 3的結果 . oracle先根據rownum <=3的條件限制選取一個范圍集合(3,1,4), 然后再在這個集合里進行排序.
order by 子句是在合適的記錄被取出后才起作用.
原來如此, 那么在oracle中如何才能實現這個功能呢?
通常我們可以采用這種辦法:
sql> select * from (select * from testsort order by id) where rownum <=3;
id
----------
1
2
3
有點麻煩,不過也只能這樣.
相同道理, 如果想從表中取出按照某字段排序前m到n條記錄
下面的oracle語句是最好的:
sql> select id from
(
select id , rownum as con from
(
select id from testsort order by id
)
where rownum <= 3 /*n值*/
)
where con >= 2; /*m 值*/
id
----------
2
3
ms sqlserver中也可以用類似的思路解決此類問題.
當然你也可以用笨一點的辦法, 比如用前n條記錄的集合minus前m-1條記錄的集合得到
前m到n條記錄集合. (有點象饒口令) , 不過ms sqlserver好象不支持minus之類的集合操作.
看來小小的一個排序取值問題還真不是那么簡單呢 !
black_snail
[email protected]
歡迎交流,轉貼請保留以上信息