簡體   English   中英

TSQL如何在解析行時迭代行?

[英]TSQL how do you iterate through rows while parsing them?

對不起,問題措辭不好,我不知道怎么形容這個。 我想迭代遍歷表中的每一行,同時這樣做,提取一個列,解析其中的varchar,並根據它找到的行插入到另一個表中。 有點像這樣:

DECLARE @string varchar(max);
foreach row in (select * from Table) {
    set @string = row[column];
    while (len(@string) > 0) {
        -- Do all the parsing in here

        if (found what was looking for)
            insert into Table2 values(row[column2], row[column3]);
    }
}

這將是一個非常好的存儲過程,因此它可以在SQL中完成。 我不太確定如何處理它。 謝謝。

編輯:

這基本上是我希望的功能:

Table 1   |
id_number | text    |
1           Hello, test 532. Yay oh and test 111   
2           test 932.
3           This is a test 315 of stuff test 555.
4           haflksdhfal test 311 sadjhfalsd
5           Yay.

我想通過這個表並解析所有文本列以查找'test#'的實例,其中#是一個數字。 當它以該格式在文本中找到某些內容時,它會將該值插入另一個表中,如:

Table 2   |
id_number | number
1           532
1           111
2           932
3           315
3           555
4           311

你在程序上思考而不是基於集合。 您可以將整個事件編寫為單個查詢:

INSERT INTO target_table (column list)
SELECT (column list)
FROM source_table
WHERE (parse your column) = (some criterion)

寫起來要容易得多,也可能更快。

如果您的解析函數很復雜,您可以將其放入用戶定義的函數中,而不是直接將其嵌入到查詢中。

在SQL Server 2008中,您可以執行此操作

WITH testTable AS
(
SELECT 1 AS id_number, N'Hello, test 532. Yay oh and test 111' AS txt UNION ALL
SELECT 2, N'test 932.' UNION ALL
SELECT 3, N'This is a test 315 of stuff test 555.' UNION ALL
SELECT 4, N'haflksdhfal test 311 sadjhfalsd' UNION ALL
SELECT 5, N'Yay.'
)

SELECT id_number,display_term
FROM testTable
CROSS APPLY sys.dm_fts_parser('"' + REPLACE(txt,'"','""') + '"', 1033, 0,0)
WHERE TXT IS NOT NULL and 
  display_term NOT LIKE '%[^0-9]%' /*Or use LIKE '[0-9][0-9][0-9]' to only get 3 
                                     digit numbers*/

返回

id_number   display_term
----------- ------------------------------
1           532
1           111
2           932
3           315
3           555
4           311

像這樣的東西你總是有“測試(數字)”。 它適用於SQL Server 2005+

DECLARE @Table1 TABLE (id_number int, textcol nvarchar(MAX))

INSERT @Table1 VALUES (1, 'Hello, test 532. Yay oh and test 111')
INSERT @Table1 VALUES (2, 'test 932.')
INSERT @Table1 VALUES (3, 'This is a test 315 of stuff test 555.')
INSERT @Table1 VALUES (4, 'haflksdhfal test 311 sadjhfalsd')
INSERT @Table1 VALUES (5, 'Yay.')


;WITH cte AS
(
    SELECT TOP 9999 CAST(ROW_NUMBER() OVER (ORDER BY c1.OBJECT_ID) AS varchar(6)) AS TestNum
    FROM sys.columns c1 CROSS JOIN sys.columns c2
)
SELECT id_number, TestNum FROM
    cte
    JOIN
    @Table1 ON PATINDEX('%Test ' + TestNum + '[^0-9]%', textcol) > 0
                    OR textcol LIKE '%Test ' + TestNum
ORDER BY
    id_number

您正在尋找的功能稱為CURSOR - 是一篇關於如何使用它們的文章。

它們被認為對性能有害並且難以正確使用。

重新思考您的問題並重申它,以便在基於集合的操作中解決它。

查看對於復雜條件使用表變量子查詢

您正在使用光標 - 請參閱此處的MSDN文檔。 請注意,應盡可能避免使用游標 - 很少有地方適合這些游標並且可能導致代碼效率低下 - 通常情況下,嘗試使用基於集合的解決方案會更好。

要按照您的要求執行此操作,可以使用Cursor進行迭代,使用下面的示例信息是光標的布局方式。 您將逐行處理放在我的評論所在的位置。

DECLARE @CurrentRecord VARCHAR(MAX)

DECLARE db_cursor CURSOR FOR  
SELECT Column
FROM Table 

OPEN db_cursor   
FETCH NEXT FROM db_cursor INTO @CurrentRecord

WHILE @@FETCH_STATUS = 0   
BEGIN   
       --Your stuff here

       FETCH NEXT FROM db_cursor INTO @name   
END   

CLOSE db_cursor   
DEALLOCATE db_cursor

但是,取決於你正在做什么,以及這是你經常做的事情。 我建議您查看是否可以將解析提取到用戶定義函數,然后您可以將其設置為基礎,而不是使用游標。 因為游標應該是“最后一搏”的努力。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM