通过jdbc执行sql比在plsql中慢好多

快乐妈妈网 2009-11-19 01:03:19
以下是我的SQL语句,表上的数据量有40多万。
SELECT SUM (T032_FORM_SU) FROM T029_FORWARD_SIJI T029 INNER JOIN T032_FORWARD_SIJIM ON
T029_WAREH_CD = T032_WAREH_CD
AND T029_OWNER_CD = T032_OWNER_CD
AND T029_SHIPMENT_ID = T032_SHIPMENT_ID
AND T032_TRAN_KBN < '3'
WHERE
T029_WAREH_CD = ?
AND T029_OWNER_CD = ?
AND T029_SLIP_KBN <> '4'
AND T029_SLIP_KBN <> '5'
AND T029_SLIP_KBN <> '9'
AND T029_SHIPMENT_KBN = '01' AND T029.T029_TRAN_KBN < '3'
通过jdbc动态绑定参数执行要10多秒才能完成,但是如果在plsql中执行,条件直接付值,也就是0.1秒左右就好了。不知道这是什么问题,而且通过jdbc执行时,如果不动态绑定参数,直接付值的话也非常快,就是一动态绑定参数,就慢了,这是什么原因。
t029是主表,t032是明细表。 这两个表都建有索引。
...全文
3546 11 打赏 收藏 转发到动态 举报
写回复
用AI写文章
11 条回复
切换为时间正序
请发表友善的回复…
发表回复
palm_civet 2009-11-29
  • 打赏
  • 举报
回复
[Quote=引用 9 楼 crazylaa 的回复:]
是否你的两个问号得数据列存在类型转换?比如你字段本来是number,而你程序中却用了setString,类型转换用了to_number函数,它就不会用你的索引了。。。
以前碰到过这个问题,也不知道说的对不对。

关注~~~
[/Quote]

这个最有可能
simple1986_2008 2009-11-29
  • 打赏
  • 举报
回复
用JDBC分析时,返回的全部的查询结果
而用PL/SQL返回的结果只是前几条记录。
crazylaa 2009-11-29
  • 打赏
  • 举报
回复
是否你的两个问号得数据列存在类型转换?比如你字段本来是number,而你程序中却用了setString,类型转换用了to_number函数,它就不会用你的索引了。。。
以前碰到过这个问题,也不知道说的对不对。

关注~~~
huangdh12 2009-11-28
  • 打赏
  • 举报
回复
可能时间都花在参数转化和数据分析上了吧。。
kbzl251 2009-11-28
  • 打赏
  • 举报
回复
关注中。。。。
pop6young 2009-11-27
  • 打赏
  • 举报
回复
[Quote=引用 2 楼 wgllz 的回复:]
我也想不同,参数不用什么计算,直接是从前台传过来的值。但就是特别的慢,如果不动态绑定,直接在sql中把值付好,执行就非常的快。
[/Quote]
桥连的肯定不如直连的快
Adebayor 2009-11-19
  • 打赏
  • 举报
回复
[Quote=引用 4 楼 wgllz 的回复:]
楼上这种说法不对呀,不可能这么慢的,我用irontrack sql跟踪了一下,要用12秒多,其中参数付值和取结果用的时间最少,最多的就是sql执行时间,能占总时间的99%
[/Quote]
就是动态绑定的问题,边解析边执行,肯定慢了
快乐妈妈网 2009-11-19
  • 打赏
  • 举报
回复
楼上这种说法不对呀,不可能这么慢的,我用irontrack sql跟踪了一下,要用12秒多,其中参数付值和取结果用的时间最少,最多的就是sql执行时间,能占总时间的99%
道光2008 2009-11-19
  • 打赏
  • 举报
回复
通过jdbc的方式,获得连接需要时间,读取sql语句到connect中需要时间,设置参数需要时间,这样不就10s啦
很正常
快乐妈妈网 2009-11-19
  • 打赏
  • 举报
回复
我也想不同,参数不用什么计算,直接是从前台传过来的值。但就是特别的慢,如果不动态绑定,直接在sql中把值付好,执行就非常的快。
horizonlyhw 2009-11-19
  • 打赏
  • 举报
回复
是不是你java端的 參數 計算的慢啊

除了jdbc的連接時間 應該不會有其他的差別了
8.用执行计划分析SQL性能      EXPLAIN PLAN是一个很好的分析SQL语句的工具,它可以在不执行SQL的情况下分析语句      通过分析,我们就可以知道ORACLE是怎样连接表,使用什么方式扫描表(索引扫描或全表扫描),以及使用到的索引名称      按照从里到外,从上到下的次序解读分析的结果      EXPLAIN PLAN的分析结果是用缩进的格式排列的,最内部的操作将最先被解读,如果两个操作处于同一层中,带有最小操作号的将首先被执行      目前许多第三方的工具如PLSQL Developer和TOAD等都提供了极其方便的EXPLAIN PLAN工具      PG需要将自己添加的查询SQL文记入log,然后在EXPLAIN PLAN中进行分析,尽量减少全表扫描      ORACLE SQL性能优化系列      1.选择最有效率的表名顺序(只在基于规则的优化器中有效)      ORACLE的解析器按照从右到左的顺序处理FROM子句中的表名,因此FROM子句中写在最后的表(基础表driving table)将被最先处理      在FROM子句中包含多个表的情况下,必须选择记录条数最少的表作为基础表      当ORACLE处理多个表时,会运用排序及合并的方式连接它们      首先,扫描第一个表(FROM子句中最后的那个表)并对记录进行排序;      然后扫描第二个表(FROM子句中最后第二个表);      最后将所有从第二个表中检索出的记录与第一个表中合适记录进行合并      例如:      表 TAB1 16,384 条记录      表 TAB2 5 条记录      选择TAB2作为基础表 (最好的方法)      select count(*) from tab1,tab2 执行时间0.96秒      选择TAB2作为基础表 (不佳的方法)      select count(*) from tab2,tab1 执行时间26.09秒      如果有3个以上的表连接查询,那就需要选择交叉表(intersection table)作为基础表,交叉表是指那个被其他表所引用的表      例如:   EMP表描述了LOCATION表和CATEGORY表的交集   SELECT *   FROM LOCATION L,   CATEGORY C,   EMP E   WHERE E.EMP_NO BETWEEN 1000 AND 2000   AND E.CAT_NO = C.CAT_NO   AND E.LOCN = L.LOCN      将比下列SQL更有效率   SELECT *   FROM EMP E ,   LOCATION L ,   CATEGORY C   WHERE E.CAT_NO = C.CAT_NO   AND E.LOCN = L.LOCN   AND E.EMP_NO BETWEEN 1000 AND 2000      2.WHERE子句中的连接顺序      ORACLE采用自下而上的顺序解析WHERE子句      根据这个原理,表之间的连接必须写在其他WHERE条件之前,那些可以过滤掉最大数量记录的条件必须写在WHERE子句的末尾      例如:   (低效,执行时间156.3秒)   SELECT *   FROM EMP E   WHERE SAL > 50000   AND JOB = 'MANAGER'   AND 25 < (SELECT COUNT(*) FROM EMP WHERE MGR=E.EMPNO);      (高效,执行时间10.6秒)   SELECT *   FROM EMP E   WHERE 25 50000   AND JOB = 'MANAGER';      3.SELECT子句中避免使用'*'      当你想在SELECT子句中列出所有的COLUMN时,使用动态SQL列引用'*'是一个方便的方法,不幸的是,这是一个非常低效的方法      实际上,ORACLE在解析的过程中,会将'*'依次转换成所有的列名      这个工作是通过查询数据字典完成的,这意味着将耗费更多的时间      4.减少访问数据库的次数

3,490

社区成员

发帖
与我相关
我的任务
社区描述
Oracle 高级技术相关讨论专区
社区管理员
  • 高级技术社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧