我在我的项目中创建了复杂的查询生成器,在测试中偶然发现了一个奇怪的问题:同一个计划的同一个查询在不同的客户机上产生不同的结果:cx_Oracle忽略order by子句,而Oracle SQLDeveloper Studio进程查询正确,但是在这两种情况下,order by present都出现在两个计划中。在
问题是:
select *
from
(
select
a.*,
ROWNUM tmp__rnum
from
(
select base.*
from
(
select id
from
(
(
select
profile_id as id,
surname as sort__col
from names
)
/* here usually are several other subqueries chained by unions */
)
group by id
order by min(sort__col) asc
) tmp
left join (profiles) base
on tmp.id = base.id
where exists
(
select t.object_id
from object_rights t
where
t.object_id = base.id
and t.subject_id = :a__subject_id
and t.rights in ('r','w')
)
) a
where ROWNUM < :rows_to
)
where tmp__rnum >= :rows_from
如果我漏掉了什么东西,我可以从cx Oracle那里进行计划:
^{pr2}$cx\u Oracle输出(似乎按id排序):
ID, Created, rownum
(1829, 2016-08-24, 1)
(2438, 2016-08-24, 2)
SQLDeveloper输出(按姓氏排序,如预期):
ID, Created, rownum
(518926, 2016-08-28, 1)
(565556, 2016-08-29, 2)
我没有看到
ORDER BY
子句会影响查询结果的顺序。在SQL中,保证结果集顺序的唯一方法是为最外层的SELECT
使用ORDER BY
子句。在在几乎所有的情况下,子查询中的
ORDER BY
不一定得到遵守(当在下一级查询中有rownum
比较时,Oracle会例外,即使在FETCH FIRST <n> ROWS
的支持下这一情况也已过时)。在因此,没有理由期望在最里面的子查询中的
ORDER BY
会有任何影响,尤其是对随后发生的JOIN
的影响。在建议:
ORDER BY
移到最外层的查询。在FETCH FIRST
语法。在ORDER BY
移到JOIN
之后。在相关问题 更多 >
编程相关推荐