当存储过程参数为大批量的字符串,并且这字符串中的值不是一个字段值的累加,而是两个或者以上字段值的累加,这种情况下怎么做最好。
具体如下:
Create procedure myproc
(
AA Varchar(4)
,BB Varchar(4)
,CC Varchar(4)
)
As
--仅仅是个例子,实际的执行语句比这要复杂,耗时
select
*
from
mytb
where
tbA=AA
and
tbB=BB
and
tbC=CC
传的参数为
'11','11','11'
'22','33','44'
'13','14','15'
'33','34','56'
'14','34','24'
'13','23','34'
............
............
............
'56','56','87'
'18','12','15'
'77','23','15'
'15','56','58'
并且这些串加起来会可能超过八千
开发环境是.NET2005+SQL2000
哪位能给个好点的策略,
希望运行时间尽可能的短,当然越简单越好
18 个解决方案
#1
什么样的情况会有传这样的值呢?
#2
你傳入的參數也是一組一組的傳吧
一組不會超過8000吧?
一組不會超過8000吧?
#3
我做的一个页面,需要从页面中的一个GridView中取出每一行的前三个字段,然后依次根据每一行的值去到几个数据表中取数据,(中间还有一些数学计算不说了),最后然后对一个计算过生成的字段做处理,所以这样传了
#4
Create procedure myproc
(
AA Varchar(4)
,BB Varchar(4)
,CC Varchar(4)
)
As
---->
Create procedure myproc
(
@AA Varchar(4)
,@BB Varchar(4)
,@CC Varchar(4)
)
As
#5
一组一组的传的话,对这些每一组抽出的数据进行综合数学计算就相当麻烦,
还有如果说我要传3000组左右的参数,这样会很慢吧
还有如果说我要传3000组左右的参数,这样会很慢吧
#6
呵呵,刚从mySql转过来,习惯还是这样写,错了。。。。。。
#7
为什么不用将页面的值放在dataset里利用数据适配器来做?
#8
数据适配器没用过,不过这个计算过程在数据适配器里面好做么,计算好像是比较麻烦,在存储过程中做这个计算倒是比较容易
#9
SQL 2005参数类型可以是Text,不知道SQL 2000是否可以。
#10
数据适配器是跟你写的存储过程相连的,其实就是数据是一条一条传进去的,而不是像你那样全进去,数据适配器是跟存储过程绑定的
#11
那样不是还是,一条一条逐条取记录么,再进行计算的时候不是还是很罗索么
#12
传的值就是如果单独传的话就是三个值,放在一起穿就是n个三个值
#13
呵呵,因为没看到你具体的计算操作,所以这里只是讨论方式而已~
#14
我也想过,如果逐条去取,然后放到c#中的datatable中,再计算,也是可以实现的,
但是要是取得次数太多的话,然后再计算的话,那就慢死了
还是希望在服务器端能处理好,我感觉更好一些,不过都比较不理想,还是想找个更好的方法。
#15
给你这样一个思路参考一下:将所有的参数传到数据库中(可以用文件传,也可以用字符串传)形成一个临时表(这里要以你的判断条件作为一条记录),让后通过系统表syscolumns来拼接成查询语句查询。
要判断的数据表:
参数临时表:
通过系统表拼成select语句where条件
执行结果:
不知这样能否实习您的需求?
要判断的数据表:
create table #tb(
id int identity(1,1),
value1 varchar(5),
value2 varchar(5),
value3 varchar(5))
insert into #tb
select 'aa','bb','cc' union
select 'dd','ee','ff' union
select 'gg','hh','ii'
参数临时表:
create table #tb1(,
id int identity(1,1),
value1 varchar(5),
value2 varchar(5),
value3 varchar(5))
insert into #tb1
select 'aa','bb','cc' union
select 'dd','dd','ff' union
select 'gg','hh','ii'
通过系统表拼成select语句where条件
declare @where varchar(500)
set @where = ''
select @where = @where +' and t0.'+name +'=t1.' + name from syscolumns
where id = object_id('#tb')
set @where = stuff(@where,1,4,'')
执行结果:
exec('select t0.* from #tb1 t0,#tb t1 where ' + @where )
不知这样能否实习您的需求?
#16
SQL 2005参数类型可以是Text,不知道SQL 2000是否可以。
#17
这样的话用2005可以。
#18
例子:例如每组有五个参数,这五个参数之间用“|”隔开,然后组与组之间用“#”隔开,如下
#|QMS1915||1||2007/08/02||1||825C2020|#
#|QMT5042||3||2007/08/02||2||825VN047|#
组成字符串
“#|QMS1915||1||2007/08/02||1||825C2020|##|QMT5042||3||2007/08/02||2||825VN047|#”
组数多了雷同
存储过程的参数设置为text类型
Create proc myproc(
@Mstr Text
)
然后传参数给该存储过程
select
AA,
BB,
CC,
DD,
EE
from
mytb
where
CHARINDEX('#|'+AA+'||'+'BB'+'||'+CC+'||'+DD+'||'+EE+'|#',@Mstr)>0
这样就可以了,如果你的字符串真的要超过text那么就没治了,
参考如下:
ntext、text 和 image
用于存储大型非 Unicode 字符、Unicode 字符及二进制数据的固定长度和可变长度数据类型。Unicode 数据使用 UNICODE UCS-2 字符集。
ntext
可变长度 Unicode 数据的最大长度为 230 - 1 (1,073,741,823) 个字符。存储大小是所输入字符个数的两倍(以字节为单位)。ntext 在 SQL-92 中的同义词是 national text。
text
服务器代码页中的可变长度非 Unicode 数据的最大长度为 231-1 (2,147,483,647) 个字符。当服务器代码页使用双字节字符时,存储量仍是 2,147,483,647 字节。存储大小可能小于 2,147,483,647 字节(取决于字符串)。
image
可变长度二进制数据介于 0 与 231-1 (2,147,483,647) 字节之间。
#|QMS1915||1||2007/08/02||1||825C2020|#
#|QMT5042||3||2007/08/02||2||825VN047|#
组成字符串
“#|QMS1915||1||2007/08/02||1||825C2020|##|QMT5042||3||2007/08/02||2||825VN047|#”
组数多了雷同
存储过程的参数设置为text类型
Create proc myproc(
@Mstr Text
)
然后传参数给该存储过程
select
AA,
BB,
CC,
DD,
EE
from
mytb
where
CHARINDEX('#|'+AA+'||'+'BB'+'||'+CC+'||'+DD+'||'+EE+'|#',@Mstr)>0
这样就可以了,如果你的字符串真的要超过text那么就没治了,
参考如下:
ntext、text 和 image
用于存储大型非 Unicode 字符、Unicode 字符及二进制数据的固定长度和可变长度数据类型。Unicode 数据使用 UNICODE UCS-2 字符集。
ntext
可变长度 Unicode 数据的最大长度为 230 - 1 (1,073,741,823) 个字符。存储大小是所输入字符个数的两倍(以字节为单位)。ntext 在 SQL-92 中的同义词是 national text。
text
服务器代码页中的可变长度非 Unicode 数据的最大长度为 231-1 (2,147,483,647) 个字符。当服务器代码页使用双字节字符时,存储量仍是 2,147,483,647 字节。存储大小可能小于 2,147,483,647 字节(取决于字符串)。
image
可变长度二进制数据介于 0 与 231-1 (2,147,483,647) 字节之间。
#1
什么样的情况会有传这样的值呢?
#2
你傳入的參數也是一組一組的傳吧
一組不會超過8000吧?
一組不會超過8000吧?
#3
我做的一个页面,需要从页面中的一个GridView中取出每一行的前三个字段,然后依次根据每一行的值去到几个数据表中取数据,(中间还有一些数学计算不说了),最后然后对一个计算过生成的字段做处理,所以这样传了
#4
Create procedure myproc
(
AA Varchar(4)
,BB Varchar(4)
,CC Varchar(4)
)
As
---->
Create procedure myproc
(
@AA Varchar(4)
,@BB Varchar(4)
,@CC Varchar(4)
)
As
#5
一组一组的传的话,对这些每一组抽出的数据进行综合数学计算就相当麻烦,
还有如果说我要传3000组左右的参数,这样会很慢吧
还有如果说我要传3000组左右的参数,这样会很慢吧
#6
呵呵,刚从mySql转过来,习惯还是这样写,错了。。。。。。
#7
为什么不用将页面的值放在dataset里利用数据适配器来做?
#8
数据适配器没用过,不过这个计算过程在数据适配器里面好做么,计算好像是比较麻烦,在存储过程中做这个计算倒是比较容易
#9
SQL 2005参数类型可以是Text,不知道SQL 2000是否可以。
#10
数据适配器是跟你写的存储过程相连的,其实就是数据是一条一条传进去的,而不是像你那样全进去,数据适配器是跟存储过程绑定的
#11
那样不是还是,一条一条逐条取记录么,再进行计算的时候不是还是很罗索么
#12
传的值就是如果单独传的话就是三个值,放在一起穿就是n个三个值
#13
呵呵,因为没看到你具体的计算操作,所以这里只是讨论方式而已~
#14
我也想过,如果逐条去取,然后放到c#中的datatable中,再计算,也是可以实现的,
但是要是取得次数太多的话,然后再计算的话,那就慢死了
还是希望在服务器端能处理好,我感觉更好一些,不过都比较不理想,还是想找个更好的方法。
#15
给你这样一个思路参考一下:将所有的参数传到数据库中(可以用文件传,也可以用字符串传)形成一个临时表(这里要以你的判断条件作为一条记录),让后通过系统表syscolumns来拼接成查询语句查询。
要判断的数据表:
参数临时表:
通过系统表拼成select语句where条件
执行结果:
不知这样能否实习您的需求?
要判断的数据表:
create table #tb(
id int identity(1,1),
value1 varchar(5),
value2 varchar(5),
value3 varchar(5))
insert into #tb
select 'aa','bb','cc' union
select 'dd','ee','ff' union
select 'gg','hh','ii'
参数临时表:
create table #tb1(,
id int identity(1,1),
value1 varchar(5),
value2 varchar(5),
value3 varchar(5))
insert into #tb1
select 'aa','bb','cc' union
select 'dd','dd','ff' union
select 'gg','hh','ii'
通过系统表拼成select语句where条件
declare @where varchar(500)
set @where = ''
select @where = @where +' and t0.'+name +'=t1.' + name from syscolumns
where id = object_id('#tb')
set @where = stuff(@where,1,4,'')
执行结果:
exec('select t0.* from #tb1 t0,#tb t1 where ' + @where )
不知这样能否实习您的需求?
#16
SQL 2005参数类型可以是Text,不知道SQL 2000是否可以。
#17
这样的话用2005可以。
#18
例子:例如每组有五个参数,这五个参数之间用“|”隔开,然后组与组之间用“#”隔开,如下
#|QMS1915||1||2007/08/02||1||825C2020|#
#|QMT5042||3||2007/08/02||2||825VN047|#
组成字符串
“#|QMS1915||1||2007/08/02||1||825C2020|##|QMT5042||3||2007/08/02||2||825VN047|#”
组数多了雷同
存储过程的参数设置为text类型
Create proc myproc(
@Mstr Text
)
然后传参数给该存储过程
select
AA,
BB,
CC,
DD,
EE
from
mytb
where
CHARINDEX('#|'+AA+'||'+'BB'+'||'+CC+'||'+DD+'||'+EE+'|#',@Mstr)>0
这样就可以了,如果你的字符串真的要超过text那么就没治了,
参考如下:
ntext、text 和 image
用于存储大型非 Unicode 字符、Unicode 字符及二进制数据的固定长度和可变长度数据类型。Unicode 数据使用 UNICODE UCS-2 字符集。
ntext
可变长度 Unicode 数据的最大长度为 230 - 1 (1,073,741,823) 个字符。存储大小是所输入字符个数的两倍(以字节为单位)。ntext 在 SQL-92 中的同义词是 national text。
text
服务器代码页中的可变长度非 Unicode 数据的最大长度为 231-1 (2,147,483,647) 个字符。当服务器代码页使用双字节字符时,存储量仍是 2,147,483,647 字节。存储大小可能小于 2,147,483,647 字节(取决于字符串)。
image
可变长度二进制数据介于 0 与 231-1 (2,147,483,647) 字节之间。
#|QMS1915||1||2007/08/02||1||825C2020|#
#|QMT5042||3||2007/08/02||2||825VN047|#
组成字符串
“#|QMS1915||1||2007/08/02||1||825C2020|##|QMT5042||3||2007/08/02||2||825VN047|#”
组数多了雷同
存储过程的参数设置为text类型
Create proc myproc(
@Mstr Text
)
然后传参数给该存储过程
select
AA,
BB,
CC,
DD,
EE
from
mytb
where
CHARINDEX('#|'+AA+'||'+'BB'+'||'+CC+'||'+DD+'||'+EE+'|#',@Mstr)>0
这样就可以了,如果你的字符串真的要超过text那么就没治了,
参考如下:
ntext、text 和 image
用于存储大型非 Unicode 字符、Unicode 字符及二进制数据的固定长度和可变长度数据类型。Unicode 数据使用 UNICODE UCS-2 字符集。
ntext
可变长度 Unicode 数据的最大长度为 230 - 1 (1,073,741,823) 个字符。存储大小是所输入字符个数的两倍(以字节为单位)。ntext 在 SQL-92 中的同义词是 national text。
text
服务器代码页中的可变长度非 Unicode 数据的最大长度为 231-1 (2,147,483,647) 个字符。当服务器代码页使用双字节字符时,存储量仍是 2,147,483,647 字节。存储大小可能小于 2,147,483,647 字节(取决于字符串)。
image
可变长度二进制数据介于 0 与 231-1 (2,147,483,647) 字节之间。