select t.parent_id
              from table(getallcode(187)) t,
                   TB_PM_JOBFORM tpj,
                   jacal.pw_core_user u,
                   jacal.pw_core_user_dept d
             where t.alldeptid = d.DEPT_ID(+)
               and tpj.entry_person_id = u.uam_id(+)
               and u.user_id = d.user_id
               and to_char(tpj.ENTRY_TIME, 'yyyy-mm-dd') between
                   '2013-01-01' and '2013-10-14'
如上语句,查询时间0.2s左右,但是一旦我 把t.parent_id改成count(t.parent_id)查询时间要70s。麻烦各位看看是什么原因,还有怎么处理?查询时间自定义函数

解决方案 »

  1.   

    count(t.parent_id) 用count(*)另外查询条件改下:
    and tpj.ENTRY_TIME between date'2013-01-01' and date'2013-10-14'
      

  2.   

      count(*) 试了 没用,条件那用date也一样,主要原因是getallcode这个函数的影响。就是不知道怎么处理
      

  3.   

    getallcode函数怎么也放到查询条件里面了你的这个结果集返回多少行,你这个函数就会被调用多少次。 如果数据量量大,那....
      

  4.   

            不怎么了解oracle 的查询机制,如果结果集返回多少行,函数被调用多少次。可以解释下如果不加count,查询结果只要0.2s跟加了count,查询结果需要70s的原因么?
      

  5.   

    你加count和不加count结果集有什么区别吗? 把执行计划贴出来看看
      

  6.   


    加count后的执行计划
      

  7.   


    select col from table;
    select count(col) from table;
    这两个查询本身就是没有可比性的,count是数据库中的一个隐式游标。第一个是将所有的数据都显示出来了,第二个是对结果进一步的进行了封装,它的效率怎么会一样呢?
      

  8.   

    你用了一个返回table类型的一个函数,建议再嵌套一层子查询试试。
    select count(*) from (select .....);
      

  9.   

        9L的方法我测试过,不行,8L我现在问题不是纠结于这两个的执行效率,我只求问题能得到解决。
      个人感觉不是count影响的原因,平时即使一个表里面有几十万条数据,count跟没有count的时间也不会相差太多,所以关键还是getallcode这个函数的影响。
      

  10.   

    ————————————————————————————————————————
    select col from table;
    select count(col) from table;
    这两个查询本身就是没有可比性的,count是数据库中的一个隐式游标。第一个是将所有的数据都显示出来了,第二个是对结果进一步的进行了封装,它的效率怎么会一样呢? 
    ——————————————————
    没有可比性
      

  11.   


    看你的执行计划,大概就是count多了一个sort,但是它是没有cost值的,对查询影响应该是不大的。
    getallcode(187) 应该好好看看你这个函数,应该主要是在这个地方,是否可以对这样函数优化一下,用另外一种方式来构造这个查询
      

  12.   


    看你的执行计划,大概就是count多了一个sort,但是它是没有cost值的,对查询影响应该是不大的。
    getallcode(187) 应该好好看看你这个函数,应该主要是在这个地方,是否可以对这样函数优化一下,用另外一种方式来构造这个查询
       函数其实也比较简单,只是为了得到这个部门树下面的所有子树。我贴一下这个函数代码如下:
       create or replace function getAllCode(deptid in varchar2)  return type_allcode
    as
      CURSOR cursor_code IS select tcd.dept_id from tb_core_dept tcd where tcd.parent_dept_id = deptid;
      cursor cursor_flag(c_flag varchar2) is select t.dept_id from tb_core_dept t 
              start with t.dept_id = c_flag connect by prior t.dept_id = t.parent_dept_id;
      flag_all type_allcode := type_allcode();
      c_row cursor_code%rowtype;
      c_flag cursor_flag%rowtype;
    begin
       for c_row in cursor_code
       loop       for c_flag in cursor_flag(c_row.dept_id)
           loop
              flag_all.extend();
              flag_all(flag_all.count) := type_code(c_row.dept_id,c_flag.dept_id);
           end loop;
       end loop;
       return flag_all;
    end getAllCode;