2012-09-02 50 views
0

我在閱讀的書中遇到了一些代碼,這讓我質疑SUBSTRING()函數的行爲。該代碼應該搜索NYSIIS替換表(語音編碼示例),並根據表中的位置'End''Mid'或'Start'替換輸入字符串的中間'N-gram'。的摘錄提供如下:T-SQL substring()行爲

NYSIIS代用表:

 
Location NGram Replacement 

Mid  A  A 
Mid  AW AA 
Mid  E  A 
Mid  EV AF 
Mid  EW AA 
Mid  I  A 
USE [AdventureWorks] 

DECLARE @Result NVARCHAR(100) = N'NEVADA'; 

DECLARE @Replacement NVARCHAR(10); 

DECLARE @i INT; 

SET @i = 1; 

WHILE @i <= LEN (@Result) 

BEGIN 

    SET @Replacement = NULL; 

    -- Grab the middle-of-name replacement n-gram 

    SELECT TOP(1) @Replacement = Replacement     
    FROM dbo.NYSIIS_Replacements       
    WHERE Location = N'Mid' 
     AND SUBSTRING(@Result, @i, LEN(NGram)) = NGram 
    ORDER BY LEN(NGram) DESC; 


    SET @Replacement = COALESCE(@Replacement, SUBSTRING(@Result, @i, 1)); 


    -- If we found a replacement, apply it 

    SET @Result = STUFF(@Result, @i, LEN(@Replacement), @Replacement) 

    -- Move on to the next n-gram 

    SET @i = @i + COALESCE(LEN(@Replacement), 1); 


END; 

SELECT @Result; 

SUBSTRING()函數遇到在表中使用「內華達爲例(「E」和「EV」 2個可能的匹配)它如何「知道」使用2字母字符串而不是那個?這是SUBSTRING()的預期行爲嗎?

我會假設@Replacement變量將同時包含「A」和「AF」,但在調試時,它只會在第一次迭代中包含「N」,在第二次迭代中只包含「AF」。

另外我不明白爲什麼TOPORDER BY被包括在這個例子中。對它們進行評論會產生相同的結果。

回答

0

ORDER BY子句使用模式的長度並按降序排序,因此最長的匹配將首先發生。 TOP子句將結果限制在第一行。刪除ORDER BY子句會導致結果不可預知。

COALESCE用於設置@Replacement要麼替換模式,或在@Result串位置@i字符如果沒有模式匹配的結果。

+0

這將是有道理的。謝謝。沒有TOP或ORDER BY的結果將無序我假設,雖然我只是每次運行它時都返回2個字母的字符串。 – voided