日期:2014-05-17  浏览次数:20852 次

提数系统中的一个查询sql执行很久很久
昨天在跑一个提数系统,后台跑到一个查询sql时就不动了,卡了很久,看了下被锁住的sql,sql如下:

select comcode,'RMB',sum(sumclaim) FROM((SELECT c.circcomcode AS ComCode,'RMB',SUM(ck.SumClaim * decode(ck.Currency,'RMB',1,decode(b.ExchRate,null,1,b.ExchRate))*decode(p.CoinsRate,null,100,p.CoinsRate)/100) AS SumClaim FROM  prpLclaim a,PrpDExch b,statcomcodemapping c ,prpLclaimLoss ck ,prpcitemcar cc,PrpCcoins p WHERE (a.EndCaseDate IS NULL OR to_date(a.EndCaseDate,'yyyy-mm-dd') > date'2013-01-31')  AND a.ClaimDate <= date'2013-01-31' AND (a.canceldate is null OR a.canceldate > date'2013-01-31') AND substr(a.InputDate,1,10) <= to_date('2013-01-31','yyyy-mm-dd') AND a.PolicyNo = p.PolicyNo(+)  AND (p.CoinsType = '1' OR p.CoinsType IS NULL)  AND b.ExchDate =     (SELECT max(ExchDate) FROM PrpDExch g      WHERE g.ExchDate<=ck.InputDate      AND g.ExchCurrency='RMB' AND ck.Currency=g.BaseCurrency(+))  AND b.BaseCurrency = ck.Currency  AND b.ExchCurrency = 'RMB'  AND a.PolicyNo = cc.PolicyNo  AND a.claimno = ck.claimno AND a.ClassCode IN  ('05','06')  AND a.ComCode = c.cciccomcode GROUP BY c.circcomcode )) GROUP BY comcode

不明白为什么会这样,因为这样的sql在系统中比比皆是,为什么到这句就卡住了,之前跑系统时从来没遇到过这种情况,换了两个数据库跑系统,都会报ORA-01652: 无法通过 128 (在表空间 TEMP 中) 扩展 temp 段这样的错,的确,在执行此sql之前,临时表空间不会有什么变化,但是到此sql,表空间突然会一直变大,直到最大空间限额,可以从2g到31g多。此sql在PL/SQL中单独执行需要耗时8.6秒左右。今天重新换了个数据库跑系统,还是出现同样的问题。网上说大量频繁的排序等操作会致使临时表空间突然增大,那么为什么在执行此sql前的N多排序sql不会出现此情况,另外,此问题该如何解决才好?我也把表空间清空并扩大了TEMP表空间,TEMP表空间是自增的,问题照样发生。这个sql有什么可以优化的地方吗?
谢谢各位!

sql

------解决方案--------------------
既然问题出在临时表空间,那就查看一下临时表空间信息:
   select * from dba_tablespaces;
   select * from dba_temp_files;
   select * from v$tempfile
然后根据再将temp数据文件自动扩展。先不管这个sql语句是否优化,做一个执行计划和统计分析,根据分析结果进行临时表的扩展。
------解决方案--------------------
select comcode, 'RMB', sum(sumclaim)
  FROM ((SELECT c.circcomcode AS ComCode,
                'RMB',
                SUM(ck.SumClaim *
                    decode(ck.Currency,
                           'RMB',
                           1,
                           decode(b.ExchRate, null, 1, b.ExchRate)) *
                    decode(p.CoinsRate, null, 100, p.CoinsRate) /