你是如何观察到这种行为的?你不执行INSERT或CREATE TABLE吗?这可以解释您的观察,因为最后,所有行都是必需的。
此外,如果您的客户设置了选项fetch all rows,则可以观察到这一点。
但在正常情况下,客户对几行Oracle 快速返回第一个连接中的第一个可用(数组大小)行忽略第二个连接.
你可以进行这个小小的Gedanken实验:
create table test1 as
select rownum id,
lpad('x',1023,'X') pad
from dual connect by level <= 1000000;
创建模拟表2到4。
现在运行您的查询(适应有效语法)
SELECT * FROM TEST1 CROSS JOIN TEST2
UNION ALL
SELECT * FROM TEST3 CROSS JOIN TEST4;
这会在大约 30 秒内返回我在 SQL Developer 中的第一页,这在某种程度上反驳了您的说法。
简单计算两个 10**6 * 10**6 笛卡尔连接所需的 TEMP 空间,行长度为 1K - 这远远高于我的 TEMP 配置。
观察Oracle实际在做什么的一种可能方法是使用/*+ gather_plan_statistics */提示运行查询。
比获取语句的SQL_ID 并检查计划中的实际行A-Rows
select * from table(dbms_xplan.display_cursor('a9y62gxagups6',null,'ALLSTATS LAST'));
SQL_ID a9y62gxagups6, child number 0
-------------------------------------
SELECT /*+ gather_plan_statistics */ * FROM TEST1 CROSS JOIN TEST2
UNION ALL SELECT * FROM TEST3 CROSS JOIN TEST4
Plan hash value: 1763392637
--------------------------------------------------------------------------------------------------------------------------------------
| Id | Operation | Name | Starts | E-Rows | A-Rows | A-Time | Buffers | Reads | Writes | OMem | 1Mem | Used-Mem |
--------------------------------------------------------------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | | 50 |00:00:28.52 | 166K| 166K| 142K| | | |
| 1 | UNION-ALL | | 1 | | 50 |00:00:28.52 | 166K| 166K| 142K| | | |
| 2 | MERGE JOIN CARTESIAN| | 1 | 1000G| 50 |00:00:28.52 | 166K| 166K| 142K| | | |
| 3 | TABLE ACCESS FULL | TEST1 | 1 | 1000K| 1 |00:00:00.02 | 4 | 28 | 0 | | | |
| 4 | BUFFER SORT | | 1 | 1000K| 50 |00:00:28.49 | 166K| 166K| 142K| 1255M| 11M| 97M (0)|
| 5 | TABLE ACCESS FULL | TEST2 | 1 | 1000K| 1000K|00:00:03.66 | 166K| 166K| 0 | | | |
| 6 | MERGE JOIN CARTESIAN| | 0 | 1000G| 0 |00:00:00.01 | 0 | 0 | 0 | | | |
| 7 | TABLE ACCESS FULL | TEST3 | 0 | 1000K| 0 |00:00:00.01 | 0 | 0 | 0 | | | |
| 8 | BUFFER SORT | | 0 | 1000K| 0 |00:00:00.01 | 0 | 0 | 0 | 1103M| 10M| |
| 9 | TABLE ACCESS FULL | TEST4 | 0 | 1000K| 0 |00:00:00.01 | 0 | 0 | 0 | | | |
--------------------------------------------------------------------------------------------------------------------------------------
你看,那个甲骨文
1) 完全扫描 table2(第 5 行)
2) 从 table1 中获取一行(第 3 行)
3) 返回前 50 行(第 0 行)
4) 表 3 和 4 未附加(第 7 行和第 9 行)
您可以简单地将示例调整为您的内部连接以查看类似的结果。