Tenho uma dúvida como você pode ver abaixo:
with cte as
(select customer_num
from vmi_segment_customer_relation
where effective_date = to_date('12/30/2021', 'mm/dd/yyyy')
and segment_id = 10000000592
)
select
t.customer_num,
cust_first_name,
cust_last_name,
cust_type_desc
from vmi_factcustomer t
join cte f
on t.customer_num = f.customer_num
and t.effective_date = to_date('12/30/2021', 'mm/dd/yyyy')
join vmi_dimcustomer d
on t.customer_num = d.customer_num;
Como você pode ver, existem três tabelas nesta consulta
1) vmi_segment_customer_relation
, Índice: "IDX1_SEGMENT"
na "segment_id"
coluna.
2) vmi_factcustomer
, Índice: "IDX1_F"
na "customer_num"
coluna.
3) vmi_dimcustomer
, Índice: "IDX_CUSTNUM"
na "customer_num"
coluna.
Todas as tabelas statistics
estão atualizadas e não há estatísticas desatualizadas. Eu peguei o real execution plan
para esta consulta usando esta dica /*+gather_plan_statistics*/
, como você pode ver, aqui está o plano:
Tenho algumas dúvidas sobre o plano:
Eu esperava que o
operation-10
estivesse sob ooperation-11
(op-10 ser o filho de op-11) porque o'IDX_CUSTNUM'
índice é para'MI_DIMCUSTOMER'
tabela! Dê uma olhadaop-5 and op-6
por exemplo. Ouop-8 and op-9
, eu esperava fazer op-10 e op-11 exatamente como os dois e não tenho ideia de por que não é!Outra questão é que, existem duas junções na consulta, então por que vemos três
Nested loop joins
no plano? Qual é a função de cada loop aninhado?
desde já, obrigado
Você parece estar atribuindo muito significado ao ID da operação. Ele existe simplesmente para identificar exclusivamente cada operação e não tem nada a ver com a ordem de execução da operação.
Você precisa ler o plano "de dentro para fora", desde a operação mais aninhada até a menos aninhada. Com isso em mente, vamos ver o que está acontecendo:
IDX1_SEGMENT
é escaneado para recuperarROWID
s correspondentes ao segmento.MI_SEGMENT_CUSTOMER_RELATION
são lidasROWID
para filtrar aquelas que correspondem àEFFECTIVE_DATE
condição e obterCUSTOMER_NUM
.CUSTOMER_NUM
valores recuperados.IDX1_F
é escaneado para encontrar as entradas correspondentesCUSTOMER_NUM
do Op. 5, e osROWID
s correspondentes são recuperados.MI_FACTCUSTOMER
são lidasROWID
para filtrar aquelas que correspondem àEFFECTIVE_DATE
condição e obterCUSTOMER_NUM
.CUSTOMER_NUM
valores do Op. 8.IDX_CUSTOMER
para buscarROWID
s correspondentes ao número do cliente.ROWID
s de Op. 10.MI_DIMCUSTOMER
para buscar as colunas necessárias.Obviamente, esses loops são executados simultaneamente: assim que o novo valor de Op. 5 estiver disponível, a próxima iteração de Ops. 9 e 8 podem prosseguir e, assim que isso for concluído, a próxima iteração de Ops. 10 e 11 podem buscar os dados necessários.
Dado o pequeno número de linhas e a presença de índices úteis, a escolha da junção de loop aninhado parece apropriada.