Oracle 19c如何获取表中最后一条记录?rownum相关疑问
Oracle 19c中ROWNUM相关问题解答
先搞懂ROWNUM的核心机制
Oracle的ROWNUM是在查询结果生成后逐行分配的序号,但它有个关键规则:只有当某一行被分配了ROWNUM=1之后,下一行才会被分配ROWNUM=2,以此类推。如果第一行不满足WHERE条件被过滤,后续行永远得不到大于1的ROWNUM值——因为ROWNUM的分配依赖前一行被保留的前提。
你的两个问题解析
1. 为什么select * from employee where rownum=(select max(rownum) from employee);无输出?
子查询select max(rownum) from employee得到的是15(因为表有15条记录),但主查询的执行逻辑是:
- Oracle先扫描employee表的第一行,给它分配ROWNUM=1,判断1是否等于15?不满足,过滤掉这行。
- 接着扫描第二行,此时因为第一行被过滤了,ROWNUM不会递增到2,还是从1开始判断,依然不等于15,继续过滤。
- 所有行都会因为这个逻辑被过滤,最终返回空结果。
2. 为什么select * from employee where rownum=2;无结果,但rownum=1可以?
这就是ROWNUM的机制导致的:
- 当你查
rownum=1时,第一行被分配ROWNUM=1,满足条件,直接返回。 - 查
rownum=2时,第一行被分配ROWNUM=1,不满足条件被过滤,此时没有行被保留,第二行永远得不到ROWNUM=2的分配——因为ROWNUM的递增必须依赖前一行被保留,所以整个结果集为空。
正确获取"最后一条记录"的方法
注意:Oracle表中的记录本身是无序的,没有天然的"最后一条",必须先通过排序定义你认为的"最后"(比如按入职时间、ID倒序等),再筛选。
方法一:子查询先分配ROWNUM再筛选
SELECT * FROM ( SELECT e.*, ROWNUM rn FROM employee e ORDER BY employee_id DESC -- 替换成你需要的排序字段,比如入职时间hire_date DESC ) WHERE rn = 1;
方法二:使用ROW_NUMBER()分析函数(更推荐)
SELECT * FROM ( SELECT e.*, ROW_NUMBER() OVER(ORDER BY employee_id DESC) rn -- 同样替换排序字段 FROM employee e ) WHERE rn = 1;
内容的提问来源于stack exchange,提问作者yyy62103
相关产品推荐
相关产品推荐

