经验分享:实例化SqlParameter时,如果是字符型,一定要指定size属性
以前在实例化SqlParameter时,通常都是用下面的语句,没有设置size属性:
- C# code
new SqlParameter("@name", SqlDbType.Varchar) { Value = name };
我一直以为是从SqlDbType类型推断,实际上是从参数的值推断,比如"ab",则size值为2,"abcd",则size值为4,且经测试发现,size的值不同时,会导致执行计划不会重用,下面的代码:
- C# code
string sql = "select top 1 * from tb where name = @o";var para = new SqlParameter("@o", SqlDbType.VarChar) {Value = "ab"};SqlHelper.ExecuteReader(ReadConnectionString, CommandType.Text, sql, para);
- SQL code
exec sp_executesql N'select top 1 * from tb where name = @o',N'@o nvarchar(2)',@o=N'ab'
- SQL code
exec sp_executesql N'select top 1 * from tb where name = @o',N'@o nvarchar(4)',@o=N'abcd'
- SQL code
--先清空执行计划缓存DBCC FREESYSTEMCACHE ('ALL')DBCC FREEPROCCACHEGOSELECT * FROM sys.dm_exec_cached_plans WHERE cacheobjtype = 'Compiled Plan'GOexec sp_executesql N'select top 1 * from tb where name = @o',N'@o nvarchar(2)',@o=N'ab'GOSELECT * FROM sys.dm_exec_cached_plans WHERE cacheobjtype = 'Compiled Plan'GOexec sp_executesql N'select top 1 * from tb where name = @o',N'@o nvarchar(4)',@o=N'abcd'GOSELECT * FROM sys.dm_exec_cached_plans WHERE cacheobjtype = 'Compiled Plan'GO
最后的说明,实例化SqlParameter时,如果是字符型,一定要指定size属性,如:
- C# code
new SqlParameter("@name", SqlDbType.Varchar, 4000) { Value = name };
[解决办法]
嗯,受教了,以前还真没注意过
[解决办法]
不错,
[解决办法]
int之类的可以不用指定,但float,decimal之类的需要指定
[解决办法]
- C# code
分享必属极品,感谢楼主分享。
[解决办法]
学无止境
[解决办法]
受教了
[解决办法]
- SQL code
SELECT est.text AS batchtext, SUBSTRING(est.text, (eqs.statement_start_offset/2)+1, (CASE eqs.statement_end_offset WHEN -1 THEN DATALENGTH(est.text) ELSE eqs.statement_end_offset END - ((eqs.statement_start_offset/2) + 1))) AS querytext, eqs.creation_time, eqs.last_execution_time, eqs.execution_count, eqs.total_worker_time, eqs.last_worker_time, eqs.min_worker_time, eqs.max_worker_time, eqs.total_physical_reads, eqs.last_physical_reads, eqs.min_physical_reads, eqs.max_physical_reads, eqs.total_elapsed_time, eqs.last_elapsed_time, eqs.min_elapsed_time, eqs.max_elapsed_time, eqs.total_logical_writes, eqs.last_logical_writes, eqs.min_logical_writes, eqs.max_logical_writes, eqs.query_plan_hash FROM sys.dm_exec_query_stats AS eqs CROSS APPLY sys.dm_exec_sql_text(eqs.sql_handle) AS estORDER BY eqs.total_physical_reads DESC
[解决办法]
支持LZ的探寻与验证的精神,赞个
[解决办法]
[解决办法]
嗯,受教了.谢谢.
[解决办法]
嗯,受教了.谢谢.
[解决办法]
老赵的文章里提到过。up
[解决办法]
- C# code
最好指定 否则会引起不必要的麻烦
[解决办法]
[解决办法]
应用程序错误啊 哎
[解决办法]
微软就是会折腾人,这要是换做Oracle,根本不需要指定,因为Oracle的输入参数,varchar2类型是不带长度的,因此你是否指定一个固定的长度,都不会影响所谓的执行计划(SQL缓存)。
[解决办法]
还有一种情况必须说明,如果你是执行存储过程,参数长度也不必指定,因为那个是由存储过程参数定义的,你实际参数的长度必须转换到存储过程声明的参数长度,这时也就不存在任何效率问题。而实际传参数多数是用在存储过程中,非存储过程一般直接拼接SQL。
[解决办法]
不明白为什么,先收藏以防不时只需
[解决办法]
[解决办法]
啊多少反而范德萨 是地方撒
[解决办法]
范德萨爱封是
[解决办法]
学习了
[解决办法]
谢谢分享
[解决办法]
学习了,楼主辛苦了
[解决办法]
跟着学习
[解决办法]
这样啊 谢谢楼主
[解决办法]
谢谢楼主分享
[解决办法]
习惯做法
- C# code
new SqlParameter("@UserID", SqlDbType.BigInt,19,ParameterDirection.Input,false,8,0,"",DataRowVersion.Current,model.UserID)//,new SqlParameter("@Name", SqlDbType.NVarChar,20,ParameterDirection.Input,false,0,0,"",DataRowVersion.Current,model.Name)//,new SqlParameter("@Password", SqlDbType.Decimal,18,ParameterDirection.Input,true,9,2,"",DataRowVersion.Current,model.Password)//,new SqlParameter("@UnitID", SqlDbType.DateTime,23,ParameterDirection.Input,true,8,3,"",DataRowVersion.Current,model.UnitID)//,new SqlParameter("@Reserved", SqlDbType.Bit,1,ParameterDirection.Input,true,1,0,"",DataRowVersion.Current,model.Reserved)//
[解决办法]
我一般都是不指定字符串大小。。看来对性能影响不小!
[解决办法]
虽然不明白楼主在说什么,但是感觉楼主很牛B
------解决方案--------------------
int当然只能到4了,int32 =4*8
[解决办法]
[解决办法]
说的没错,不过使用sqlhelper的语法会更简单哦!新版本去http://www.dbhelper.org/sqlhelper/下载吧
[解决办法]
[解决办法]
以前从来不设的,现在看来需要设一下
[解决办法]
这个问题可能我已经遇到N次了,以前经常出现网站无法访问,一直没有找到原因。。。
很可能就是楼主说的这个问题。。。
谢啦。。。
[解决办法]
多谢,
看了你的文章感觉我的路还长着
[解决办法]
学习了!!
[解决办法]
了。
[解决办法]
学习了。