不使用 rownum 检索特定行
Retrieve specific rows without using rownum
由于我不能在查询中使用 rownum
,我如何使用 rowid
使用 rowid
或其他可能的解决方案从第二行到第四行获取结果 rownum
.
这是我当前的查询,它将检索第 2 行和第 4 行:
SELECT * FROM Record a
WHERE
2 = (SELECT COUNT (rowid)
FROM Record b
WHERE a.rowid >= b.rowid)
UNION
SELECT * FROM Record a
WHERE
4 = (SELECT COUNT (rowid)
FROM Record c
WHERE a.rowid >= c.rowid);
也许还有其他更好的方法? TQ
如果不能用rownum
,那就用row_number()
:
SELECT a.*
FROM (SELECT a.*, ROW_NUMBER() OVER (ORDER BY rowid) as seqnum
FROM Record a
) a
WHERE seqnum BETWEEN 2 and 4;
注意:??
用于排序列。 SQL 表表示 无序 集,因此没有第一行或第二行的概念,除了引用排序列。为此,您可以使用 rowid
。
在 Oracle 12c 中,您将使用 OFFSET
/FETCH
:
SELECT a.*
FROM Record a
OFFSET 1 ROWS
FETCH FIRST 3 ROWS ONLY;
我应该指出您可以使用rownum。你就是做不到:
SELECT a.*
FROM Record a
WHERE rownum BETWEEN 2 and 4;
您可以在子查询中使用它:
SELECT a.*
FROM (SELECT a.*, rownum as seqnum
FROM Record a
) a
WHERE seqnum BETWEEN 2 and 4;
请注意,如果没有 ORDER BY
,则无法保证结果以任何顺序返回,包括 rowid
顺序。
使用 Oracle 12c,您现在可以轻松地进行行限制。在您的场景中,您可以这样做:
SELECT *
FROM RECORD
OFFSET 1 ROWS FETCH NEXT 1 ROWS ONLY
UNION
SELECT *
FROM RECORD
OFFSET 3 ROWS FETCH NEXT 1 ROWS ONLY
如果您想避免 rownum
和 row_number
,请使用 sum
:
select *
from (
select sum(1) over ( order by rowid /* or whatever you need */ ) as rn,
r.*
from record
)
where rn between 2 and 4
诀窍仅在于,这里 sum(1)
给出的结果与 count(1)
或 count(rowid)
或任何 count
在 not null
值上给出的结果相同,这与使用 row_number
或 rownum
计算行数是一回事。
通过这种方式,您可以使用 sum
来计算 row_number
,而无需显式写入“row_number
”或“rownum
”。
SQL> create table testTab(x) as ( select level from dual connect by level <= 6);
Table created.
SQL> select t.*,
2 count(1) over (order by rowid desc) as count,
3 sum(1) over (order by rowid desc) as sum,
4 row_number() over (order by rowid desc) as rowNumber
5 from testTab t;
X COUNT SUM ROWNUMBER
---------- ---------- ---------- ----------
6 1 1 1
5 2 2 2
4 3 3 3
3 4 4 4
2 5 5 5
1 6 6 6
外部查询只是应用过滤器。
由于我不能在查询中使用 rownum
,我如何使用 rowid
使用 rowid
或其他可能的解决方案从第二行到第四行获取结果 rownum
.
这是我当前的查询,它将检索第 2 行和第 4 行:
SELECT * FROM Record a
WHERE
2 = (SELECT COUNT (rowid)
FROM Record b
WHERE a.rowid >= b.rowid)
UNION
SELECT * FROM Record a
WHERE
4 = (SELECT COUNT (rowid)
FROM Record c
WHERE a.rowid >= c.rowid);
也许还有其他更好的方法? TQ
如果不能用rownum
,那就用row_number()
:
SELECT a.*
FROM (SELECT a.*, ROW_NUMBER() OVER (ORDER BY rowid) as seqnum
FROM Record a
) a
WHERE seqnum BETWEEN 2 and 4;
注意:??
用于排序列。 SQL 表表示 无序 集,因此没有第一行或第二行的概念,除了引用排序列。为此,您可以使用 rowid
。
在 Oracle 12c 中,您将使用 OFFSET
/FETCH
:
SELECT a.*
FROM Record a
OFFSET 1 ROWS
FETCH FIRST 3 ROWS ONLY;
我应该指出您可以使用rownum。你就是做不到:
SELECT a.*
FROM Record a
WHERE rownum BETWEEN 2 and 4;
您可以在子查询中使用它:
SELECT a.*
FROM (SELECT a.*, rownum as seqnum
FROM Record a
) a
WHERE seqnum BETWEEN 2 and 4;
请注意,如果没有 ORDER BY
,则无法保证结果以任何顺序返回,包括 rowid
顺序。
使用 Oracle 12c,您现在可以轻松地进行行限制。在您的场景中,您可以这样做:
SELECT *
FROM RECORD
OFFSET 1 ROWS FETCH NEXT 1 ROWS ONLY
UNION
SELECT *
FROM RECORD
OFFSET 3 ROWS FETCH NEXT 1 ROWS ONLY
如果您想避免 rownum
和 row_number
,请使用 sum
:
select *
from (
select sum(1) over ( order by rowid /* or whatever you need */ ) as rn,
r.*
from record
)
where rn between 2 and 4
诀窍仅在于,这里 sum(1)
给出的结果与 count(1)
或 count(rowid)
或任何 count
在 not null
值上给出的结果相同,这与使用 row_number
或 rownum
计算行数是一回事。
通过这种方式,您可以使用 sum
来计算 row_number
,而无需显式写入“row_number
”或“rownum
”。
SQL> create table testTab(x) as ( select level from dual connect by level <= 6);
Table created.
SQL> select t.*,
2 count(1) over (order by rowid desc) as count,
3 sum(1) over (order by rowid desc) as sum,
4 row_number() over (order by rowid desc) as rowNumber
5 from testTab t;
X COUNT SUM ROWNUMBER
---------- ---------- ---------- ----------
6 1 1 1
5 2 2 2
4 3 3 3
3 4 4 4
2 5 5 5
1 6 6 6
外部查询只是应用过滤器。