在不能改变sql文本,以及sta跑不出我们希望的执行计划的情况下,可以通过改写sql,添加适合hint后,生成sql plan baseline 固定到原sql上面,从而达到改变原sql执行计划的目的,具体步骤:
1、给原sql(命名为sql1)生成执行计划基线
DECLARE
l_plans_loaded PLS_INTEGER;
BEGIN
l_plans_loaded := DBMS_SPM.load_plans_from_cursor_cache(
sql_id => sql1的sql_id,
plan_hash_value=>sql1的plan hash value);
END;
/
2、给改写后的sql(命名为sql2)生成执行计划基线
DECLARE
l_plans_loaded PLS_INTEGER;
BEGIN
l_plans_loaded := DBMS_SPM.load_plans_from_cursor_cache(
sql_id => sql2的sql_id,
plan_hash_value=>sql2的plan hash value,
sql_handle =>sql1在步骤一中所产生的基线的sql_handle);
END;
/
3、删除sql1在第一步中生成的sql执行计划基线
DECLARE
v_text PLS_INTEGER;
BEGIN
v_text := DBMS_SPM.drop_sql_plan_baseline(
sql_handle => sql1在步骤一中锁产生的基线的sql_handle,
plan_name => sql1在步骤一中所产生的基线的plan_name);
DBMS_OUTPUT.put_line(v_text);
END;
/
此时查看DBA_SQL_PLAN_BASELINES可以看到sql已经成功绑定了新的执行计划基线