求oracle分页查询语句方案oracle的分页语句我已经知道
在网上查了一下,大概都是这些:
SELECT /*+ FIRST_ROWS */ * FROM
(
SELECT A.*, ROWNUM RN
FROM (SELECT * FROM TABLE_NAME) A --不排序
WHERE ROWNUM <= 40
)
WHERE RN >= 21;SELECT /*+ FIRST_ROWS */ *
FROM (SELECT a.*, row_number() over(ORDER BY 1) rn--假排序,速度同上
FROM t1 a)
WHERE rn BETWEEN 21 AND 40;SELECT *
FROM (SELECT a.*, row_number() over(ORDER BY c1) rn --真实排序,无法比较速度
FROM t1 a)
WHERE rn BETWEEN 21 AND 40;我想问的是:你怎么保证你下一次查询时,结果集还是按照原来查询的顺序排列的呢?
如果不能保证,那你在查询下一页内容就是不是对应上次查询的下一页内容,比如:第一次查询,结果集是这样的:
1,a
2,b
3,c
4,d
5,f
6,e
7,f
8,g
9,h
10,i如果用上述语句:假如结果集而是:
1,a
2,b
3,c
4,d
5,f那我想查询下一页内容,应该是:
6,e
7,f
8,g
9,h
10,i你怎么保证一定就是这5条呢?
它不一定还是按照第一次查询的顺序排列的啊,结果集可能是:
1,h
2,g
3,c
4,a
5,p
这个我已经实际验证过了,真的不是第一查询的顺序。
所以才会问这个问题,不知各位前辈怎么样用oracle做分页查询的?
希望赐教。
在网上查了一下,大概都是这些:
SELECT /*+ FIRST_ROWS */ * FROM
(
SELECT A.*, ROWNUM RN
FROM (SELECT * FROM TABLE_NAME) A --不排序
WHERE ROWNUM <= 40
)
WHERE RN >= 21;SELECT /*+ FIRST_ROWS */ *
FROM (SELECT a.*, row_number() over(ORDER BY 1) rn--假排序,速度同上
FROM t1 a)
WHERE rn BETWEEN 21 AND 40;SELECT *
FROM (SELECT a.*, row_number() over(ORDER BY c1) rn --真实排序,无法比较速度
FROM t1 a)
WHERE rn BETWEEN 21 AND 40;我想问的是:你怎么保证你下一次查询时,结果集还是按照原来查询的顺序排列的呢?
如果不能保证,那你在查询下一页内容就是不是对应上次查询的下一页内容,比如:第一次查询,结果集是这样的:
1,a
2,b
3,c
4,d
5,f
6,e
7,f
8,g
9,h
10,i如果用上述语句:假如结果集而是:
1,a
2,b
3,c
4,d
5,f那我想查询下一页内容,应该是:
6,e
7,f
8,g
9,h
10,i你怎么保证一定就是这5条呢?
它不一定还是按照第一次查询的顺序排列的啊,结果集可能是:
1,h
2,g
3,c
4,a
5,p
这个我已经实际验证过了,真的不是第一查询的顺序。
所以才会问这个问题,不知各位前辈怎么样用oracle做分页查询的?
希望赐教。
解决方案 »
- 江湖救急 oracle改名风波
- 求动态分区表完整SQL代码
- 我们单位想请人在Oracle平台下,帮我们做一个C/S结构与B/S结构相结合的数据库,我不太懂,不知道这样说对不对,刚才让各位高手笑话了,真的很惭愧!!!
- 请教高手
- revoke问题,用户权限无法撤销?
- 关于oracle字符编码的问题
- (急)一个表结构很简单的sql问题,请教oracle中是否能实现?
- oracle中如何用一条delete语句删除多张表中的记录?
- 正版Oracle9i fot NT安装时到哪里输入序列号增加用户数(在线等待)
- 存储函数里面的动态Select语句的问题!!!!!
- oracle 没有的数据补0
- [Oracle]JAVA传字符串数组给存储过程(function)问题,有数组长度各个数组元素为空。
SELECT /*+ FIRST_ROWS */ * FROM
(
SELECT A.*, ROWNUM RN
FROM (SELECT * FROM TABLE_NAME) A --不排序
WHERE ROWNUM <= 40
)
WHERE RN >= 21;按照ROWNUM来分页的话,的确有可能出现排序不一致,可能性的大小取决你表的数据被更新,删除的频度,在真实应用里的变化一般可以忽略,由于他速度最快,一般都用这个如果一定要严格的排序的话,一般在第一种的语句上做变化,如下
SELECT /*+ FIRST_ROWS */ * FROM
(
SELECT A.*, ROWNUM RN
FROM (SELECT * FROM TABLE_NAME ORDER BY ..) A --排序
WHERE ROWNUM <= 40
)
WHERE RN >= 21;第三种的话,使用分析函数,太耗资源了,不建议这么用,尤其大数据量的前提下
(
select t.*,rownum rr from v_view_forta t
) b
where b.rr between 5 and 8
order by b.rr--1,13 表中group字段
020801
020801
020801
0201
01050310
021201
021201
021201
03060306
0212
021301-- 11,13 表中group字段 ,正确
0306
0212
021301
-- 5,8 表中group字段 正确
0105
0310
021201
021201
select k.*,rownum rr from v_view_forta k
where rownum between 2 and 6
-- 1,10
0101
0101
0104
0104
01050105
0110
011002
011002
011002-- 2,6 结果集为空!!!-- 这样写结果同上
/*select g.*,rownum rr from v_view_forta g
where rownum>=3 and rownum<=10*/
select * from
(
select d.*,rownum rr from v_view_forta d
) p
where p.rr>=2 and p.rr<=7-- 1,10
020801
020801
020801
0201
01050310
021201
021201
021201
0306
-- 2,7 正确
020801
020801
0201
0105
0310
021201/*结论:使用rownum做分页查询,必须将rownum放在子查询内!否则不起作用!!!*/
这是我得出的结论,不知大家有何见解,集思广益,希望大家献计献策,感激不尽!
在数据库解析完查询语句之后,并且在查询语句做任何的排序或者聚合之前,ROWNUM被赋值,就是在查询的时候已经被赋值了 所以在这个基础上取的数据 看出来的效果就是数据库默认的排序效果
假设表名tb1 表字段id,no 取分组排序后的5-10条数据
select *
from (
select a.*,
row_number() over(partition by a.no order by a.id) rn
from tb1 a
)t1
where rn > 4 and rn <10
这个和rownum效果差不多 必须要在子查询里面进行排序后 才能在外层取的想要的排序后的数据
where rownum>=3 and rownum<=10查到的是空?