SQL:如何正确区分字符串中的所有单词,除非它们 <= 3 个字符

问题描述

我正在寻找 sql 函数,该函数将查看字符串和每个单词的大小写,除非它是

例如:

2021 雪佛兰 Silverado Ltz

会变成

2021 雪佛兰 Silverado LTZ


2020 本田思域LX轿车

会来

2020 款本田思域 LX 轿车

我编写了一个函数来查看整个字符串及其长度,我只是不确定如何查看由空格分隔的每个项目。这是我现在拥有的功能

ALTER FUNCTION [dbo].[ucwords] (@InputString VARCHAR(4000),@wordsLongerThan INT = -1 )
RETURNS VARCHAR(4000)
AS
BEGIN
IF @InputString IS NULL
    RETURN NULL;

IF (@wordsLongerThan <> -1 AND LEN(@InputString) < @wordsLongerThan)
    return @InputString;

DECLARE @Index INT
DECLARE @Char CHAR(1)
DECLARE @OutputString VARCHAR(255)

SET @OutputString = LOWER(@InputString)
SET @Index = 2
SET @OutputString = STUFF(@OutputString,1,UPPER(SUBSTRING(@InputString,1)))

WHILE @Index <= LEN(@InputString)
BEGIN
    SET @Char = SUBSTRING(@InputString,@Index,1)
    IF @Char IN (' ',';',':','!','?',','.','_','-','/','&','''','(')
    IF @Index + 1 <= LEN(@InputString)
BEGIN
    IF @Char != ''''
    OR
    UPPER(SUBSTRING(@InputString,@Index + 1,1)) != 'S'
    SET @OutputString =
    STUFF(@OutputString,1)))
END
    SET @Index = @Index + 1
END

RETURN ISNULL(@OutputString,'')
END

解决方法

如果您使用的是 SQL Server 2016,请尝试以下操作:

CREATE OR ALTER FUNCTION dbo.ucwords ( 
    @Sentence varchar(4000)
)
RETURNS varchar(4000)
WITH RETURNS NULL ON NULL INPUT
AS
BEGIN

    DECLARE @Cased varchar(4000) = '';  --<-- initializing to an empty string is important.

    SELECT
        @Cased = @Cased + ' ' + CASE 
            WHEN LEN ( Word ) <= 3 THEN UPPER ( Word )
            ELSE UPPER ( LEFT ( Word,1 ) ) + LOWER ( RIGHT ( Word,LEN ( Word ) - 1 ) )
        END
    FROM ( 
        
        SELECT value AS Word FROM STRING_SPLIT ( @Sentence,' ' )

    ) AS Words;

    RETURN LTRIM ( @Cased );

END
GO

然后尝试:

SELECT dbo.ucwords ( '2020 HONDA CIVIC LX SEDAN' ) AS [ucwords];

退货

+---------------------------+
|          ucwords          |
+---------------------------+
| 2020 Honda Civic LX Sedan |
+---------------------------+

也试试:

SELECT dbo.ucwords ( '2021 CHEVROLET Silverado Ltz' ) AS [ucwords];

退货

+------------------------------+
|           ucwords            |
+------------------------------+
| 2021 Chevrolet Silverado LTZ |
+------------------------------+
,

在 DB Compat 130 及更高版本中,您可以在函数中使用 STRING_SPLIT 和 STRING_AGG 来拆分句子,使用 LEN 查看它是否超过 3 个字符并相应地设置大小写:

ALTER FUNCTION [dbo].[ucwords] (@InputString VARCHAR(4000),@wordsLongerThan INT = -1 )
RETURNS VARCHAR(4000)
AS
BEGIN
IF @InputString IS NULL
    RETURN NULL;

IF (@wordsLongerThan <> -1 AND LEN(@InputString) < @wordsLongerThan)
    return @InputString;

DECLARE @StringAsTable TABLE (
    RowNum INT IDENTITY(1,1),StringVal VARCHAR(4000)
)
DECLARE @OutputString VARCHAR(255)

INSERT @StringAsTable(StringVal)
SELECT value  
FROM STRING_SPLIT(@InputString,' ')  
WHERE RTRIM(value) <> '';

UPDATE @StringAsTable
SET StringVal = UPPER(StringVal)
WHERE LEN(StringVal) <= 3;

UPDATE @StringAsTable
SET StringVal = UPPER(LEFT(StringVal,1)) + LOWER(SUBSTRING(StringVal,2,LEN(StringVal)))
WHERE LEN(StringVal) > 3;

SELECT @OutputString = STRING_AGG(StringVal,' ') WITHIN GROUP (ORDER BY RowNum ASC)
FROM @StringAsTable ;

RETURN ISNULL(@OutputString,'');
END