快速加入两个大桌子

时间:2018-11-20 15:39:11

标签: oracle

在通过查询进行研究并进行在线研究之后,我求助您。期待您的答复!我正在尝试以一种通用的方式编写此文档,因为我正在寻找有关如何执行此操作的通用想法,而不是确切的陈述。如果对此问题的反馈不佳,我很乐意对其进行重新整理,让我知道。我们开始:

我有两个表:

  • 表1具有10条MIO记录。它只有一列:
    • A列:唯一ID(例如'5uz1g09aksmsd'文本)
  • 表2具有300条MIO记录。它有两列:
    • A列:唯一ID(例如'5uz1g09aksmsd'文本)
    • B列:一个数字(例如32.5432)

目前还没有索引等,甚至没有PK,因为这两个表都是通过CTAS创建的。这两个表都已分析。

我现在正在寻找一个快速查询(准备工作,例如创建索引可能要花些时间,没问题),以创建包含表1的10个MIO行和表2的B列的第三个表。通过A列找到(对于99%,将找到一个匹配项)。为了更加清楚,一个简单的CTAS可能是:

create table3 as
select t1.a, 
    (select t2.b from table2 t2 where t2.a = t1.a and rownum = 1)
    -- the rownum = 1 is to show Oracle that there can only be one match
from table1 t1;

这不是最快的速度(我希望如此)。您有什么想法使其更快?创建索引?哪个?您想在执行计划中看到哪种联接?哈希联接?我已经找到了

  • 创建表nologging
  • 并行查询执行和并行表创建

但是,我对允许我们更改系统(例如创建索引)的完美执行计划的具体外观感兴趣。特别是我要的是11gR2,但也欢迎12c注释。

1 个答案:

答案 0 :(得分:2)

使用此查询从最简单的可能性开始

create table c as 
select /*+ parallel(6) */ a.a, b.b 
from a 
left outer join b
on a.a = b.a
;

它将使用哈希联接,根据您的硬件设置调整并行度。

预期执行计划如下

    --------------------------------------------------------------------------------------------------------------------------
| Id  | Operation                        | Name     | Rows  | Bytes | Cost (%CPU)| Time     |    TQ  |IN-OUT| PQ Distrib |
--------------------------------------------------------------------------------------------------------------------------
|   0 | CREATE TABLE STATEMENT           |          |   261M|  6238M| 56799   (1)| 00:03:48 |        |      |            |
|   1 |  PX COORDINATOR                  |          |       |       |            |          |        |      |            |
|   2 |   PX SEND QC (RANDOM)            | :TQ10002 |   261M|  6238M| 31984   (1)| 00:02:08 |  Q1,02 | P->S | QC (RAND)  |
|   3 |    LOAD AS SELECT                | C        |       |       |            |          |  Q1,02 | PCWP |            |
|*  4 |     HASH JOIN OUTER              |          |   261M|  6238M| 31984   (1)| 00:02:08 |  Q1,02 | PCWP |            |
|   5 |      PX RECEIVE                  |          |  7849K|    44M|   726   (1)| 00:00:03 |  Q1,02 | PCWP |            |
|   6 |       PX SEND HASH               | :TQ10000 |  7849K|    44M|   726   (1)| 00:00:03 |  Q1,00 | P->P | HASH       |
|   7 |        PX BLOCK ITERATOR         |          |  7849K|    44M|   726   (1)| 00:00:03 |  Q1,00 | PCWC |            |
|   8 |         TABLE ACCESS STORAGE FULL| A        |  7849K|    44M|   726   (1)| 00:00:03 |  Q1,00 | PCWP |            |
|   9 |      PX RECEIVE                  |          |   261M|  4741M| 31149   (1)| 00:02:05 |  Q1,02 | PCWP |            |
|  10 |       PX SEND HASH               | :TQ10001 |   261M|  4741M| 31149   (1)| 00:02:05 |  Q1,01 | P->P | HASH       |
|  11 |        PX BLOCK ITERATOR         |          |   261M|  4741M| 31149   (1)| 00:02:05 |  Q1,01 | PCWC |            |
|  12 |         TABLE ACCESS STORAGE FULL| B        |   261M|  4741M| 31149   (1)| 00:02:05 |  Q1,01 | PCWP |            |
--------------------------------------------------------------------------------------------------------------------------


Predicate Information (identified by operation id):
---------------------------------------------------

   4 - access("A"."A"="B"."A"(+))

我对您大小的综合数据进行的测试是35秒。