select count(distinct a.nlyzxmbh) as c_xm,sum(isnull(a.zgrs,0)) as sum_zgs,sum(isnull(gzze,0)) as sum_gzze,sum(isnull(lrze,0)) as sum_nlr,sum(isnull(sj,0)) as sum_nsj,sum(isnull(zjz,0)) as sum_zjz,sum(isnull(a.cz,0)) as sum_ncz,sum(isnull(a.swfcz,0)) as sum_htyz from t_neilianyinzi a where 1=1 and a.nlyzxmbh in ( select a.nlyzxmbh from v_neilianyinzi a where 1=1 and a.tj='省级已审核' and 1=1 and 1=1 and 1=1 and a.dwzjrq>='2010-05-01' and a.dwzjrq <='2008-06-31' group by a.nlyzxmbh having sum(isnull(a.td,0)+isnull(a.tjs,0)+isnull(a.sb,0)+isnull(a.ldjqt,0))>0 )我想这里主要是有一个in操作符,
但我不知道该如何来优化。因为这个in中的结果集有时会上万。
如果要实现t_neilianyinzi.nlyzxmbh =v_neilianyinzi.nlyzxmbh是不是会快些,但这个怎么实现呢。

解决方案 »

  1.   

    改成INNER JOIN,所有条件列上加索引
      

  2.   

    但在子查询中有group by a.nlyzxmbh having sum(isnull(a.td,0)+isnull(a.tjs,0)+isnull(a.sb,0)+isnull(a.ldjqt,0))>0 )
    这个如何处理,不能放在外面来吧。
      

  3.   

    SELECT ...
    FROM T1
    INNER JOIN (
    SELECT ...
    WHERE ...    --这里的条件加索引
    GROUP BY ... --这里加索引 
    ) T2 ON T1.ID1=T2.ID2  --这里加索引
      

  4.   

    a.nlyzxmbh这个是主键,是会自动建索引的吧。
      

  5.   

    直接改成这样,看看结果应该相同select 
    count(distinct a.nlyzxmbh) as c_xm,
    sum(isnull(a.zgrs,0)) as sum_zgs,
    sum(isnull(gzze,0)) as sum_gzze,
    sum(isnull(lrze,0)) as sum_nlr,
    sum(isnull(sj,0)) as sum_nsj,
    sum(isnull(zjz,0)) as sum_zjz,
    sum(isnull(a.cz,0)) as sum_ncz,
    sum(isnull(a.swfcz,0)) as sum_htyz 
    from t_neilianyinzi a 
    where 1=1 and a.tj='省级已审核' and a.dwzjrq>='2010-05-01' and a.dwzjrq <='2008-06-31' 
    and  (select sum(isnull(a.td,0)+isnull(a.tjs,0)+isnull(a.sb,0)+isnull(a.ldjqt,0))
    from t_neilianyinzi where nlyzxmbh=a.nlyzxmbh)>0--或者
    select 
    count(distinct a.nlyzxmbh) as c_xm,
    sum(isnull(a.zgrs,0)) as sum_zgs,
    sum(isnull(gzze,0)) as sum_gzze,
    sum(isnull(lrze,0)) as sum_nlr,
    sum(isnull(sj,0)) as sum_nsj,
    sum(isnull(zjz,0)) as sum_zjz,
    sum(isnull(a.cz,0)) as sum_ncz,
    sum(isnull(a.swfcz,0)) as sum_htyz 
    from t_neilianyinzi a 
    where 1=1 and a.tj='省级已审核' and a.dwzjrq>='2010-05-01' and a.dwzjrq <='2008-06-31' 
    and  exists(select 1 
    from t_neilianyinzi 
    where nlyzxmbh=a.nlyzxmbh 
    and (td>0 or tjs>0 or sb>0 or ldjqt>0)
    )
      

  6.   

    不是,子表中的不是t_neilianyinzi,而是v_neilianyinzi
      

  7.   

    看下查询计划,分析性能瓶颈在外部查询还是内部子查询。优化外部查询:
    t_neilianyinzi.nlyzxmbh上加索引;
    优化内部子查询:
    v_neilianyinzi.tj和v_neilianyinzi.dwzjrq上加索引;
    v_neilianyinzi.nlyzxmbh上有聚集索引更好。
    如果v_neilianyinzi是视图的话,检查视图的语句是否需要优化。
      

  8.   

    t_neilianyinzi a
    v_neilianyinzi a
    这两个地方最好不要用同样的别名,容易出错。
      

  9.   

    LZ的性能瓶颈估计并不在in操作符。IN多数情况下并不比JOIN效率低。为了代码逻辑的可读性,有时候用IN也是可以的。另外,LZ最好讲究一下代码格式。如果那堆SQL是字符串拼接尚可理解,如果是写在存储过程里的那就不可原谅。
      

  10.   

    谢谢,t_neilianyinzi有2W条数据,v_neilianyinzi是t_neilianyinzi和t_daoweizijin的联合查询视图,t_daoweizijin有3W条数据。现在是要进行一些统计报表,其中报表中每一个数据基本上都是统计得到的,所以,速度特别的慢。搞不下去了。只能通过一边统计,一边建立统计结果文件,统计一条就建一条,到最后一起下载了。如果想直接显示在一个网页上,就不可能了。难道是视图的问题?
      

  11.   

    视图在2005以后可以建聚集索引,但加了索引就变味了,属于物化视图。所以,你这个应用情况下,就不要考虑对视图建索引了。。参考feilu的做些索引调整。
      

  12.   

    先不考虑索引视图(物化视图)。在v_neilianyinzi.tj和v_neilianyinzi.dwzjrq上加索引;就是说tj和dwzjrq从哪个表来,就在哪个表的这个字段上建索引。v_neilianyinzi是t_neilianyinzi和t_daoweizijin的联合查询视图。这两个表的JOIN条件字段要有索引(最好是聚集索引)。需要的话不妨把视图定义也贴出来。
      

  13.   


    数据库服务器在本机还是远程,使用上都没有区别,都要用客户端去连。
    只要你能用Management Studio或查询分析器连上去,该看到的都能看到。