zoukankan      html  css  js  c++  java
  • SQL Server 中获取字符串拼音的标量函数实现

        工作中时常遇到字符串转换为拼音的需求。特别目前在各大网站平台都可以看到的基于拼音的查询功能。如果在查询中增加相应的拼音查询,就可以减少很多的因中文汉字完全输入的不便利,例如:当我要查询叫”郭德纲“人员时,直接输入"GDG"即可,这样是不是比较方便输入。
        
        中文汉字有个特点:同字不同音 。在不同的语境或中文汉字组合时,会出现不同的读法。比如:参加会议中的”参“和中药材人参中“参”是两个不同的读音,诸如这样的中文汉字有不少的。本版块的实现也存在这样的问题。可以通过项目或平台基于使用中文多音字的频率来选择同一的转换,比如说:你所在的公司是中药材有关的行业,就可以将“参”对应的字母匹配为“S";如果你所在的公司具有起人名的业务,可以将中文汉字”查“(姓氏读查,如查良庸----起笔名为金庸)的字母匹配为”C“等等。
     
     1 IF OBJECT_ID(N'dbo.ufn_Pinyin', N'FN') IS NOT NULL
     2 BEGIN
     3     DROP FUNCTION dbo.ufn_Pinyin;
     4 END
     5 GO
     6  
     7 --==================================
     8 -- 功能: 获取字符串的拼音
     9 -- 说明: 针对中文汉字的多音字情况,可以在函数中增加多音字的字母匹配,缺点就是以后遇到该中文汉字不论其作出语境如何都会按照其多音字的字母匹配。
    10 -- 作者: XXX
    11 -- 创建: XXXX-XX-XX
    12 -- 修改: XXX-XXX-XX XXX XXXXXXXX
    13 -- 调用: SELECT dbo.ufn_Pinyin(N'中国') AS Pinyin; 
    14 --==================================
    15 CREATE FUNCTION dbo.ufn_Pinyin
    16 (
    17     @chvnStr NVARCHAR(4000)                -- 字符串
    18 ) RETURNS NVARCHAR(4000)
    19     --$Encode$--
    20 AS
    21 BEGIN
    22     -- NULL默认值处理
    23     SET @chvnStr = ISNULL(@chvnStr, N'');
    24  
    25     -- 声明局部变量
    26     DECLARE 
    27         @intLen AS INT, 
    28         @chvnPinyin AS NVARCHAR(4000),
    29         @chnCharacter AS NCHAR(1);
    30     -- 初始化局部变量
    31     SELECT
    32         @intLen = 0,
    33         @chvnPinyin = N'',
    34         @chnCharacter = N'';
    35  
    36     -- 插入的字符串为空字符串则直接返回该函数
    37     IF @chvnStr = N''
    38     BEGIN
    39         RETURN @chvnPinyin;
    40     END
    41  
    42     -- 声明中文汉字的局部表变量
    43     DECLARE @tblChineseCharacter TABLE (
    44         ChineseCharacter NCHAR(1) COLLATE Chinese_PRC_CI_AS NOT NULL,
    45         Letter NCHAR(1) NOT NULL
    46     );
    47  
    48     -- 向中文汉字的局部表变量插入数据
    49     INSERT INTO @tblChineseCharacter (ChineseCharacter, Letter)
    50     SELECT N'', N'A' UNION ALL SELECT N'', 'B' UNION ALL SELECT N'', 'C' UNION ALL SELECT N'', N'D' UNION ALL
    51     SELECT N'', N'E' UNION ALL SELECT N'', 'F' UNION ALL SELECT N'', 'G' UNION ALL SELECT N'', N'H' UNION ALL
    52     SELECT N'', N'J' UNION ALL SELECT N'', 'K' UNION ALL SELECT N'', 'L' UNION ALL SELECT N'', N'M' UNION ALL
    53     SELECT N'', N'N' UNION ALL SELECT N'', 'O' UNION ALL SELECT N'', 'P' UNION ALL SELECT N'', N'Q' UNION ALL
    54     SELECT N'', N'R' UNION ALL SELECT N'', 'S' UNION ALL SELECT N'', 'T' UNION ALL SELECT N'', N'W' UNION ALL
    55     SELECT N'', N'X' UNION ALL SELECT N'', 'Y' UNION ALL SELECT N'', 'Z' UNION ALL SELECT N'', N'S' /*增加多音字的字母匹配*/;
    56  
    57     -- 获取字符串的长度
    58     SET @intLen= LEN(@chvnStr);
    59  
    60     WHILE @intLen >= 1 /*@intLen > 0*/
    61     BEGIN
    62         -- 从后往前逐次获取单个字符
    63         SET @chnCharacter = SUBSTRING(@chvnStr, @intLen, 1);
    64  
    65         -- 获取当前字符对应的字母
    66         SELECT TOP 1 @chvnPinyin = Letter + @chvnPinyin
    67         FROM @tblChineseCharacter
    68         WHERE ChineseCharacter <= @chnCharacter 
    69         ORDER BY ChineseCharacter DESC;
    70  
    71         -- 如果当前受影响的行数为0,则表示当前字符可能是中文外的其他字符,如英文字符等等
    72         IF @@ROWCOUNT = 0
    73         BEGIN
    74             SET @chvnPinyin = SUBSTRING(@chvnStr, @intLen, 1) + @chvnPinyin;            
    75         END
    76  
    77         -- 字符串长度局部变量递减
    78         SET @intLen = @intLen - 1;
    79     END
    80  
    81     RETURN @chvnPinyin;
    82 END
    83 GO

    演示该函数的效果,如下的T-SQL:

    1 SELECT dbo.ufn_Pinyin(N'中国') AS ColName,dbo.ufn_Pinyin(N'中国ilove你') AS Col2Name, dbo.ufn_Pinyin(N'中国我爱你') AS Col3Name;
    2 GO

    执行的后的查询结果如下:

     
    博友有解决中文多音字的拼音字母匹配的好方案,也请不吝赐教,万分感谢。
     
    注意:该以上实现如果存在侵权,也请原作者提出来,谢谢。
  • 相关阅读:
    javaweb基础(6)_servlet配置参数
    javaweb基础(5)_servlet原理
    读书笔记:java特种兵(上)
    基础算法(四):海量数据的处理方法
    基础算法(三)动态规划和贪心算法
    基础算法(二):堆排序,快速排序
    基本算法(一):插入排序,归并排序
    JVM基础和调优(六)
    JVM基础和调优(五)
    JVM基础和调优(四)
  • 原文地址:https://www.cnblogs.com/dzy863/p/5056320.html
Copyright © 2011-2022 走看看