SQL循环自增存储过程

  用SQL语句实现数据库某表某列(如ID,OrderID等整型字段)的值循环自增,一直以来是我梦寐以求想实现的功能,却由于知识有限而无法顺利找到有效的解决方法,导致在工作上用了不少笨方法来拐弯抹角去实现功能。直到某次本人做的数据整理小工具,还是无法将用户录入那些不规范的条目顺利排序起来而开始发飚,烦恼之际,回想起SQL数据库里有存储过程和用户自定义函数,都能利用while语句实现循环,或许可以找到有效的好方法,于是往这方面开辟新的解决方法。

  鉴于之前曾使用过用户自定义函数,编写过按特殊字符分离字符串的函数,有点小成功。此次无例外,结果一试便知错了,函数无法动态传递表名,即定义带参数的函数,如@TableName,编写select * from @TableName,SQL不认变量,认为@TableName未声明,这就给本来想编写灵活性高点的函数带来困难。用set @SQL='select '+@count+'=count(*) from '+@TableName,exec(@SQL),又无法获取执行sql语句后的@count值,只有直接这样写:Select @count=count(*) from tablename才能成功获取,此处tablename不能为变量,必须是数据库实实在在存在的表名。此外还有重要的一点是,怎样获取排列好的数据集里的ID?!以便在while里循环使用update语句时,能用上where id=@id按顺序定位每条记录,限制一条接一条记录有序自增,而不是批量update自增到最大值?!实在是太吃屎了,无奈之下放弃用户自定义函数,转向存储过程。

  存储过程和用户自定义函数一样吃屎,依然无法动态传递表名,但有个优点是,能使用exec('select * from '+@TableName)。NND,怎么我在自定义函数里用exec老提示:在函数内的 'EXECUTE STRING' 中对带副作用的或依赖于时间的运算符的使用无效,或者是找不到存储过程?!还是存储过程妥。之前提到重要的一点转到存储过程还有待解决,这时只好求助强大的百度大侠了,强人牛人依然一大群,提倡利用游标移动来实现定位。数据库中游标的概念,虽然之前听说过,但从来没使用过也不懂使用,不过还真是给了我初享沐浴之甘露般的惊喜。

  开始声明个游标,就遇到要动态传递表名的情况,还好有exec使用sql语句变量组合代替,有了成功定位的方法,后面的问题便迎刃而解。好了,上面说了一堆废话,该上自己的研究成果了~

Create Procedure [dbo].[UpdateOrderID]
 @TableName varchar(8000),  --表名参数
 @ColumnName varchar(8000), --列名参数(要循环自增的字段)
 @OrderFileds varchar(8000) --排序字段参数
as
begin tran --开始事务
 declare @SQL varchar(8000)
 declare @ID int
 declare @index int
 declare @count int
 
--声明游标
--select ID from (select * from jjda)t 用于从记录集里再次查询记录
exec('declare CRMPSContact_cursor cursor for select ID from '+@TableName+' order by '+@OrderFileds)
--打开游标
open CRMPSContact_cursor
--取第一行的值给专案变量: @ID
fetch next from CRMPSContact_cursor into @ID
set @index=1
--select @count=rows from sysindexes where indid in (0,1) and object_name(id)=@TableName  计算表条目总数赋值给变量:@count
--移动游标,其它所有行更新操作(当到结尾时退出)
while @@FETCH_STATUS = 0
begin
 set @SQL='update '+@TableName+' set '+@ColumnName+'='+cast(@index as varchar(8000))+' where id='+cast(@ID as varchar(8000))
 exec(@SQL)
 set @index=@index+1
 --游标移到下一行
 fetch next from CRMPSContact_cursor into @ID
 --执行错误回滚
 if @@error!=0
 begin
  rollback tran
  return
 end
end
--提交所有变更
commit tran
--关闭游标
close CRMPSContact_cursor
--释放游标
deallocate CRMPSContact_cursor
--恢复设置
set nocount off

  这样,UpdateOrderID编写好后,在SQL 2005里右击该存储过程,选择执行存储过程,输入三个参数@TableName,@ColumnName,@OrderFileds的值执行便可看到效果。在SQL 2000里就没那么顺利了,首先右击该存储过程,就没有执行存储过程的菜单选项。无奈只能使用普通的sql语句去执行了,打开某个表切换到sql语句和数据条目分栏模式或查询分析器里,输入语句:exec UpdateOrderID @TableName='****',@ColumnName='****',@OrderFileds='****',其中****代表要传入的值,点击“!”运行即出效果。

  妥!很妥!非常妥!相当妥!妥得不能再妥!

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

CSICSICSICSI

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值