以下为sql server的存储过程: create procedure Pro_GenerateID ( @tableName varchar(50), --要产生递增号的表名 @columnName varchar(50), --要产生递增号的列名 @signID varchar(20) --标记符,如是以G-1,G-2,G-3...形式递增,如果给@signID传递'G-'则返回G-4 ) as declare @signLength int, --@signID的长度 @strScript varchar(800), --产生递增id的sql字符串 @strIntScript varchar(200) --当前表最大ID号的sql字符串 set @signLength = len(@signID) select @strIntScript='cast(substring(' + @columnName + ',' + cast((@signLength + 1) as varchar(20)) + ',(select max(len(' + @columnName + ')) from ' + @tableName +')-' +cast(@signLength as varchar(20)) + ') as int)' select @strScript='select top 1 (''' + @signID + ''' + cast((' + @strIntScript + '+1) as varchar(20))) as id from ' + @tableName + ' where left(' + @columnName + ',' + cast(@signLength as varchar(20)) + ')=''' + @signID + ''' order by ' + @strIntScript + ' desc' select @strScript='if(exists(select * from ' + @tableName + ' where ' + @columnName + ' like ''' + @signID + '%'')) ' + @strScript +' else select ''' + (@signID +'1') + ''' as id' print @strScript exec(@strScript) 如果在ccc表中没有数据 执行此存储过程:exec Pro_GenerateID 'ccc','c1','G-' 显示结果为: id ------ G-1 (返回 1 行) ______________________________________________________________________________________________ 答1: 在c#中定义类可以写: Public Class GenerateIncreaseID{ public static string GetNewID(string tableName,string columnName,string signID){ SqlConnection con = new SqlConnection("..."); SqlCommand com = new SqlCommand("Pro_GenerateID",con); com.CommandType = CommandType.StoredProcedure; com.Parameters.Add(new SqlParameter("@tableName",tableName)); com.Parameters.Add(new SqlParameter("@columnName",columnName)); com.Parameters.Add(new SqlParameter("@signID",signID)); try{ con.Open(); return com.ExecuteScalar().ToString(); } catch(Exception ex){ throw(ex); } finally{ if(con.State == ConnectionState.Open){ con.Close(); } con = null; com = null; } } } 调用时只需: string s = GenerateIncreaseID.GetNewID("ccc","c1","G-"); 可以用此方法来生成有规则主键,表中标识符等. ---------------------------------------------------------------------------------------------- SQL SERVER中的三种获得自增长ID的方法 这个功能比较常用,所以记下来以防自己忘掉。 SCOPE_IDENTITY 返回插入到同一作用域中的 IDENTITY 列内的最后一个 IDENTITY 值。一个作用域就是一个模块——存储过程、触发器、函数或批处理。因此,如果两个语句处于同一个存储过程、函数或批处理中,则它们位于相同的作用域中。 IDENT_CURRENT 返回为任何会话和任何作用域中的指定表最后生成的标识值。这个函数需要一个以表名为值的变量,也就是说虽然不受会话和作用域的限制,却会受到表的限制。 @@IDENTITY 返回最后插入的标识值。 体会:加上事物处理,两个函数一个变量没有本质区别。不加事物处理两个函数一个变量受到其他会话、作用域的影响不一样。 一直以来都是使用@@identity来获得最后一个插入到表的记录的identity值,最近发现这种方法在某种情况是不可靠的,先来看看两个概念 作用域:在SQLSERVER作用域就是一个模块-存储过程,触发器,函数或批处理 会话: 一个用户连接产生的所有上下文信息(online book找不到会话的概念,参照会话上下文概念而写) 相同点:都是返回最后插入的标识值 不同点: @@identity :返回当前会话最后一个标识值,不限于特定的作用域 ; ident_current('tablename'):返回任何会话,任何作用域中的指定表中生成的最后一个标识值 ; scope_identity :返回当前会话当前作用域任何表生成的最后一个标识值 。
posted on 2007-09-19 19:38  gerdy  阅读(456)  评论(0编辑  收藏  举报