最近为了优化数据库执行效率,把原有代码中的用得最频繁的数据库操作改成了参数化查询的方式,但是。有个带有in的sql语句,就让人郁闷了。数据库中的数据老是没更新,检查了半天,最后还是把DEBUG_MODE编译参数打开,查看出错信息,才定位到错误。
    'sqlStr = "update tbCommand set isHandled = 1 where id IN (?);"
执行时出错,将varchar转换成bigint时出错。只好改成
    sqlStr = "update tbCommand set isHandled = 1 where id=?;"
然后在一个循环中逐个更新。
网上也没找到这个问题的较好的解决方法。
msdn上有一篇HOW TO: Implement Helper Class to use a SqlParameter with a list of values in a IN clause,竟是用了临时表。不知道有没人遇到过类似问题,最后是怎么解决的?

解决方案 »

  1.   

        cmdCommandUpdate.CommandText = sqlStr
        Set param = cmdCommandUpdate.CreateParameter("IDS", adVarChar, adParamInput, 1000)
        cmdCommandUpdate.Parameters.Append param是字符串的。我也不知道这种情况下该用什么数据类型的
    以前直接写in (" & strID & ");"
    strid="4,5,6"
    也是可以的。
      

  2.   

    拼接字符串是可以的,参数化不行.
    in()语句里面包含的内容在数据库里不是简单的字符型,其中的逗号含义用自己赋值进去的变量不能取代.
    我一般用的就是传一个字符串进去,然后在数据库存储过程里分割.
    或者用临时表类型:declare @t as table(col varchar(10))
      

  3.   

    用临时表 和在代码里直接用for循环分割,再一个一个地update,哪个效率高?
    看起来差不多吧。
      

  4.   

    Sql中split方法实现http://9bugaosu1.blog.163.com/blog/static/6272222520107214106342/
      

  5.   

    给个样子吧,一般我不说这个方法的
    declare @code as varchar(10)
    declare @t table(col varchar(10))while(charindex('#',@codes)<>0)   --@codes 是传进来的参数
    begin
        insert @t(col) values (substring(@codes,1,charindex('#',@codes)-1))   
    set @codes = stuff(@codes,1,charindex('#',@codes),'')   
    end
    if len(@codes)>=8 and len(@code)<=10
    insert @t(col) values (@codes) update tableB set field2='Yes' where field1 in(select col from @t)
      

  6.   

    上例是我用到的一个存储过程里面的
    @code 一般长度为8-10 ,故条件视你自己的情况而定
      

  7.   

    除非这些 id 是用户随意选择的,否则应该换成选取这些 id 子查询的条件。
      

  8.   

    MS的参数化查询已经帮我们优化了,如果连续多条Update语句的话,效率会大幅提高!详见SQLServer的事件查看器。至于跟临时表对比,我没有测试过,不下结论。
      

  9.   

    一般情况下ID都是有规律的,比如在一定的范围以内,可以考虑使用Between。
      

  10.   

    所谓参数化查询,就是将你sql语句中的?号作为对象来处理的,它不是将对象解析成字符串来处理你的n子句,这也是参数化查询能够防范sql注入的原因...
    如果你in子句要处理比如4,5,6三个值,就要将sql语句解析成三个参数:
    sqlStr = "update tbCommand set isHandled = 1 where id IN (?,?,?);"还有关于参数的赋值处理,你可以参考,希望对你有帮助:http://blog.csdn.net/vbman2003/archive/2010/12/06/6057503.aspx
      

  11.   

    这里4 5 6在SQL server的in中是整型数据(int或bigint),你的id是字符型(varchr),当id里没有数字以外的字符时是可以的(varchar到bigint的转换在SQL server里是隐性自动转换的),如果有则出错。最好的方法是strid="'4','5','6'",带单引号则不会出错。
      

  12.   

    那篇blog看了。有些地方值得借鉴。
    不过,事先并不知道 IN 后面的参数个数,所以。。
      

  13.   

    不过,事先并不知道 IN 后面的参数个数,所以。。
    ----------------------------------------
    这种情况经常用到的,实际上就是拼接sql语句...