有人可以帮助我调整这个查询,因为我是oracle中性能调优的新手。
INSERT INTO mdm_id_relation
SELECT
pat_key, hub_pat_id, msa_pat_id, pat_id
FROM
ods_raw_patient_mdm_process p1
WHERE NVL (pat_id, 'NULL') IN (SELECT pat_id
FROM mdm_id_relation)
AND NOT EXISTS (SELECT pat_key
FROM mdm_id_relation p2
WHERE p1.pat_key = p2.pat_key);
答案 0 :(得分:0)
要调整INSERT查询,您需要使用以下内容:
测试查询的地方。理想情况下,它是一个单独的数据库,但也可以使用单独的模式。最小化所涉及的表和索引的副本。 原因: INSERT会更改数据,您需要运行不同版本的查询,直到您对性能感到满意为止。
测试表需要具有与真实表完全相同的结构,并且与真实表的数据量大致相同。 原因: INSERT的性能在很大程度上取决于结构和数量。
最新统计信息:查找DBMS_STATS.GATHER_TABLE_STATS
以及如何使用它。 原因:让查询优化器有机会找到一个好的查询计划。
衡量效果的方法(挂钟秒或Oracle成本等),甚至更好地访问查询计划(SQL Developer:Explain Plan按钮,或者查看William' s)脚本)。
当我需要调整INSERT
语句时,我通常从SELECT
部分开始,直到我对它感到满意为止。首先运行SELECT ...
,如果没问题,我运行CREATE TABLE foo NOLOGGING AS SELECT ...
来测量所有行的SELECT。如果没关系,我会测试整个INSERT ... SELECT ...
语句。
答案 1 :(得分:0)
性能方面的任何问题都是select
,而不是insert
。我认为这是一个等价的查询:
INSERT INTO mdm_id_relation (pat_key, hub_pat_id, msa_pat_id, pat_id) -- always list the columns!
SELECT pat_key, hub_pat_id, msa_pat_id, pat_id
FROM ods_raw_patient_mdm_process p1
WHERE EXISTS (SELECT 1
FROM mdm_id_relation mir
WHERE mir.pat_id = p1.pat_id
) AND
NOT EXISTS (SELECT 1
FROM mdm_id_relation mir
WHERE p1.pat_key = mir.pat_key
);
对于此查询,您需要两个索引:mdm_id_relation(pat_id)
和mdm_id_relation(pat_key)
。这些应该对性能有很大帮助。
注意:在插入之前先测试select
。