我有一个场景,其中我有一个存储过程,其中包含一组sql语句(连接和子查询的组合,查询对于显示来说很大) 最后结果存储在临时表中。
这是由用户从前端或程序员从具有特定权限的后端执行的。
这里的问题是,此查询的执行时间存在差异。
有时它需要10分钟,有时需要1个小时,但平均经过的时间是10分钟,一个常见的事情是它总是提供相同数量的记录(大致相同)。
答案 0 :(得分:1)
正如ErikL提到的,检查查询的执行计划是一个好的开始。在Oracle 11g
中,您可以使用DBMS_PROFILER
。这将为您提供有关违规陈述的信息。我会多次运行它,看看多个运行时间之间有什么区别。首先检查您是否安装了DBMS_PROFILER
。我相信它是一个单独的包。
启动探查器:
SQL> execute dbms_profiler.start_profiler('your_procedure_name');
运行存储过程:
SQL> exec your_procedure_name
停止探查器:
SQL> execute dbms_profiler.stop_profiler;
这将显示商店过程中的所有语句及其相关的运行时间,这样您就可以将问题缩小到可能导致差异的单个查询。
以下是Oracle
上的DBMS_PROFILER
文档:
Oracle DBMS PROFILER
答案 1 :(得分:1)
如果您是oracle的新手,那么您可以使用dbms_output或使用日志记录表来存储中间执行时间,这样您就可以知道哪个SQL导致了该问题。
declare
run_nbr number;
begin
run_nbr = 1; -- or get it from sequence
SQL1;
log(run_nbr ,user,'sql1',sysdate);
SQL2;
log(run_nbr ,user,'sql2',sysdate);
commit;
end;
这里的日志过程只不过是简单的插入语句,它会插入到表中的“LOG”中,并且列的最小值为run_nbr,user,sql_name,execution_date
procedure log(run_nbr number, user varchar2, sql_name varchar2, execution_date date)
is
begin
insert into log values(run_nbr, user, sql_name, execution_date);
-- commit; -- Un-comment if you are using pragma autonomous_transaction
end;
放置这些日志语句只需要很少的时间,但可以让您了解执行时间。稍后一旦你知道了这个问题,你只需删除/注释这些行,或者在没有这些日志语句的情况下对原始过程进行代码备份,并在指出问题后重新编译它。
答案 2 :(得分:0)
我会检查查询的执行计划,也许那里的配置文件并不总是使用。
答案 3 :(得分:0)
或者如果没有解决它,您还可以尝试跟踪从前端调用SP的会话。关于跟踪的解释非常好:http://tinky2jed.wordpress.com/technical-stuff/oracle-stuff/what-is-the-correct-way-to-trace-a-session-in-oracle/