2011-09-28 46 views
0
MERGE INTO Analysis a 
USING (SELECT * FROM Data) b 
ON (a.User_Id = b.User_Id AND a.Upgrade_Flag = 0) 
WHEN MATCHED THEN 
UPDATE SET Status = NVL(a.Status, 'ACTIVATE'); 

上面的查询工作fine.But当数以百万计的记录都存在,这可能会导致性能issue.Is有以上查询的任何替代方案,以获得更好performace.Please建议我对此感谢您的时间性能问题,我的建议query.Please

+0

你能向我们展示一份执行计划吗? –

+0

性能调整是证据收集的问题。所以你需要提供更多的信息。两个表的数据量,数据分布以及哪些列被编入索引。同时解释查询计划和统计数据。同时指示性的时间,包括你认为应该是一个合理的时间。最后,背景:这是一项常规工作还是一次性? – APC

回答

0

该查询看起来不错。也许你应该创建一些索引?

为Analysis.User_Id创建索引并为Data.User_Id创建索引(如果尚未创建)(主键自动创建索引)。

或者也可能为包含User_Id和Upgrade_Flag列的Analysis创建索引。

+0

Juho:@peter索引已经创建。但是,自从有数万亿条记录以后,它能否随时带来性能问题? – user472625

1

没有看到执行计划,我无法预测替代方案是否会更有效。但我注意到,您不使用更新中合并源,这表明这可能改写一个简单的更新语句:

UPDATE Analysis a 
SET Status = NVL(a.Status, 'ACTIVATE') 
WHERE a.Upgrade_Flag = 0 
AND a.User_Id IN (
    SELECT b.User_Id FROM Data b 
) 

由于总是有这些东西的话,你必须使用之间的选择正如我所示的IN子句或带有相关子查询的EXISTS子句。通常,当试图调整性能时,测试两个选项都是值得的,但至少在某些情况下,优化器会自行尝试这种转换。

0

这真的不是很明显,为什么你使用MERGE而不是简单的更新。

update analysis a 
set a.status = 'ACTIVATE' 
where a.status is null 
and a.upgrade_flag = 0 
and a.user_id in (select b.user_id from data b) 
/

从数据中只选择USER_ID,而不是整个记录可以加快速度的,假定DATA.USER_ID索引。