前段時間,在做一個可以批量審核或刪除資料的功能時,遇到這麼個問題:
因為審核或刪除操作是在預存程序進行的,所以,就打算將選中的資料的主鍵拼成字串,傳到預存程序進行分離,再繼續處理。
C#中和JavaScript中都有相應的分離字串的Split函數,就想當然的以為SQL中也會有類似的函數,結果查了半天的MSSQL協助文檔,也沒找到。沒辦法,只好自己寫了,在網上搜了下相關的,看了一兩篇關於SQL分離字串的自訂函數的文章,結果,有點失望,可能是自己水平差,或者是因為人家的代碼沒寫注釋吧,總之就是看著挺吃力的,還沒看完就決定自己寫了。。。
思路很簡單:在需要分解的字串中,如果存在指定的分隔字元,則將第一個分隔字元前面的字串取出,存入表內,然後在需要分解的字串中將已取出的字串及第一個分隔字元刪除,然後繼續下一次分解如果還存在指定的分隔字元,就分解)
以下是SQL:
- -- =============================================
- -- Author: Henson
- -- Create date: 2011-04-20
- -- Description: 字串分離函數
- -- =============================================
- ALTER FUNCTION [dbo].[Split]
- (
- @strText varchar(3000),--待分離的原字串
- @strSplit varchar(100)--分隔字元
- )
- RETURNS @temp Table
- (
- ID int IDENTITY PRIMARY KEY,
- SingleVal varchar(1000)
- )
- AS
- BEGIN
- Declare @intLen int --用來儲存待分離原字串長度
- Declare @intSplitLen int --分隔字元長度
- Declare @intIndex int --用來儲存分離字串在原字串的位置
- Declare @strVal varchar(1000)--用來儲存分離出來後的字串
- --擷取原字串的長度
- Set @intLen = LEN(RTRIM(LTRIM(@strText)))
- Set @intSplitLen = LEN(RTRIM(LTRIM(@strSplit)))
- --原字串不為空白,才繼續分離
- If(@intLen > 0)
- Begin
- --迴圈原字串,直至原字串被分離完畢
- While CHARINDEX(@strSplit,@strText)>0
- Begin
- --擷取分離字串在原字串的位置
- Set @intIndex = CHARINDEX(@strSplit,@strText)
- --擷取分離出的字串,並插入表中
- Set @strVal = RTRIM(LTRIM(LEFT(@strText,@intIndex-1)))
- if(LEN(@strVal)>0)
- Begin
- Insert Into @temp (SingleVal) values(@strVal)
- End
- --分離後,將分離出的字串包括分隔字元)從原字串中刪除
- Set @strText = Substring(@strText,@intIndex+@intSplitLen,@intLen-@intIndex)
- --重新設定原字串的長度
- Set @intLen = LEN(@strText)
- End
- --如果分離後的原字串依然不為空白,則也應該插入表中
- if(LEN(RTRIM(LTRIM(@strText)))>0)
- Begin
- Insert Into @temp (SingleVal) values(@strText)
- End
- End
- return
- END
分隔字元允許是多位的)
按一般的習慣來說,在組織多個字串時,一般都是這種寫法:strKeys += strSingleKey + ",";
所以可能最終該字串可能會以逗號結尾,如果組織完成後,將結尾的逗號去掉了,那就不會以逗號結尾,所以,在迴圈分解完成後,如果剩下的原字串中去除左右空格後),如果還有內容 ,則也應該存入表中。
可能我這種寫法不是最好的,也可能會有問題,如確實有需要改進的,還請指出,不勝感激!!!