6
4

2 に答える 2

7

以下を利用する必要があります。通常、次の 3 つの組み合わせが必要です。

  1. patindex
  2. charindex
  3. substring

上記のコメントに応えてpatindex、ケースが見つかった場合は 0 にしないでください。patindexは、指定されたパターンの開始位置を見つけます。そのためpatindex、ケースが見つかった場合は、整数 > 0 を返す必要があります。

編集:

また、特定の機会に重宝しますlen(string)reverse(string)

于 2013-06-06T22:34:25.837 に答える
5

CLR および .NET プロジェクトを SQL Server に公開すると、非常に効率的です。過去 2 年間、2005 SQL Server で VB.Net の CLR プロジェクトを使用し始めた後、.NET バージョンに置き換えた TSQL でスカラー関数が発生するたびに、パフォーマンス時間が劇的に改善されることがわかりました。高度な日付操作、書式設定と解析、文字列の書式設定と解析、MD5 ハッシュ生成、ベクトルの長さ、文字列 JOIN 集計関数、テーブル値の分割関数、共有フォルダーを介したシリアル化されたデータテーブルからの一括読み込みにも使用しました (これは驚くべきことです)。速い)。

RegEx については、まだ存在していないため、コンパイルされた EXE が同じ REGEX を実行するのと同じくらい効率的であるとしか考えられません。つまり、非常に高速です。

いくつかの RegEx 機能を可能にする VB.Net CLR プロジェクトのコード ファイルを共有します。このコードは、サーバーに発行される .NET CLR DLL の一部になります。

機能概要

Regex_IsMatch(Data,Parttern,Options) AS tinyint (0/1 結果)

例えば。SELECT dbo.Regex_IsMatch('Darren','[trwq]en$',NULL) -- 1 / true を返します

Regex_Group(data,pattern,groupname,options) as nvarchar(max) (キャプチャ グループ値が返されます)

例えば。SELECT dbo.Regex_Group('Cable 180+e10 to 120+e3',' (?[0-9]+)+e[0-9]+','n',NULL) -- '180' を返します

Regex_Replace(data,pattern,replacement,options) as nvarchar(max) (変更された文字列を返します)

例えば。SELECT dbo.Regex_Replace('ケーブル 180+e10 から 120+e3',' (?[0-9]+)+e(?[0-9]+)',' ${e}:${n]' ,NULL) -- 「ケーブル 10:180 から 3:120」を返します

Partial Public Class UserDefinedFunctions

    ''' <summary>
    ''' Returns 1 (true) or 0 (false) if a pattern passed is matched in the data passed.
    ''' Returns NULL if Data is NULL.
    ''' options example, full or partial names can be used after slashes or hypens with or without spaces, some are exclusive of each other "/ic /ex -s" = "\ignorecase -explicitcapture/singleline"
    ''' </summary>
    ''' <param name="data"></param>
    ''' <param name="pattern"></param>
    ''' <param name="options">options example, full or partial names can be used after slashes or hypens with or without spaces, some are exclusive of each other "/ic /ex -s" = "\ignorecase -explicitcapture/singleline"</param>
    ''' <returns></returns>
    ''' <remarks></remarks>
    <Microsoft.SqlServer.Server.SqlFunction()> _
    Public Shared Function Regex_IsMatch(data As SqlChars, pattern As SqlChars, options As SqlString) As SqlByte
        If pattern.IsNull Then
            Throw New Exception("Pattern Parameter in ""RegEx_IsMatch"" cannot be NULL")
        End If
        If data.IsNull Then
            Return SqlByte.Null
        Else
            Return CByte(If(Regex.IsMatch(data.Value, pattern.Value, Regex_Options(options)), 1, 0))
        End If
    End Function

    ''' <summary>
    ''' Returns the Value of a RegularExpression Pattern Group by Name or Number.
    ''' Group needs to be captured explicitly. Example Pattern "[a-z](?&lt;m&gt;[0-9][0-9][0-9][0-9])" to capture the numeric portion of an engeneering number by the group called "m".
    ''' Returns NULL if The Capture was not successful.
    ''' Returns NULL if Data is NULL.
    ''' options example, full or partial names can be used after slashes or hypens with or without spaces, some are exclusive of each other "/ic /ex -s" = "\ignorecase -explicitcapture/singleline"
    ''' </summary>
    ''' <param name="data"></param>
    ''' <param name="pattern"></param>
    ''' <param name="groupName">Name used in the explicit capture group</param>
    ''' <param name="options">options example, full or partial names can be used after slashes or hypens with or without spaces, some are exclusive of each other "/ic /ex -s" = "\ignorecase -explicitcapture/singleline"</param>
    <Microsoft.SqlServer.Server.SqlFunction()> _
    Public Shared Function Regex_Group(data As SqlChars, pattern As SqlChars, groupName As SqlString, options As SqlString) As SqlChars
        If pattern.IsNull Then
            Throw New Exception("Pattern Parameter in ""RegEx_IsMatch"" cannot be NULL")
        End If
        If groupName.IsNull Then
            Throw New Exception("GroupName Parameter in ""RegEx_IsMatch"" cannot be NULL")
        End If
        If data.IsNull Then
            Return SqlChars.Null
        Else
            Dim m As Match = Regex.Match(data.Value, pattern.Value, Regex_Options(options))
            If m.Success Then
                Dim g As Group
                If IsNumeric(groupName.Value) Then
                    g = m.Groups(CInt(groupName.Value))
                Else
                    g = m.Groups(groupName.Value)
                End If
                If g.Success Then
                    Return New SqlChars(g.Value)
                Else ' group did not return or was not found.
                    Return SqlChars.Null
                End If
            Else 'match failed.
                Return SqlChars.Null
            End If
        End If
    End Function

    ''' <summary>
    ''' Does the Equivalent toi Regex.Replace in .NET.
    ''' Replacement String Replacement Markers are done in this format "${test}" = Replaces the capturing group (?&lt;test&gt;...)
    ''' If the replacement pattern is $1 or $2 then it replaces the first or second captured group by position.
    ''' Returns NULL if Data is NULL.
    ''' options example, full or partial names can be used after slashes or hypens with or without spaces, some are exclusive of each other "/ic /ex -s" = "\ignorecase -explicitcapture/singleline"
    ''' </summary>
    ''' <param name="data"></param>
    ''' <param name="pattern"></param>
    ''' <param name="replacement">Replacement String Replacement Markers are done in this format "${test}" = Replaces the capturing group (?&lt;test&gt;...). If the replacement pattern is $1 or $2 then it replaces the first or second captured group by position.</param>
    ''' <param name="options">options example, full or partial names can be used after slashes or hypens with or without spaces, some are exclusive of each other "/ic /ex -s" = "\ignorecase -explicitcapture/singleline"</param>
    ''' <returns></returns>
    ''' <remarks></remarks>
    <SqlFunction()> _
    Public Shared Function Regex_Replace(data As SqlChars, pattern As SqlChars, replacement As SqlChars, options As SqlString) As SqlChars
        If pattern.IsNull Then
            Throw New Exception("Pattern Parameter in ""Regex_Replace"" cannot be NULL")
        End If
        If replacement.IsNull Then
            Throw New Exception("Replacement Parameter in ""Regex_Replace"" cannot be NULL")
        End If
        If data.IsNull Then
            Return SqlChars.Null
        Else
            Return New SqlChars(Regex.Replace(data.Value, pattern.Value, replacement.Value, Regex_Options(options)))
        End If
    End Function

    ''' <summary>
    ''' Buffered list of options by name for speed.
    ''' </summary>
    Private Shared m_Regex_Buffered_Options As New Generic.Dictionary(Of String, RegexOptions)(StrComp)
    ''' <summary>
    ''' Default regex options used when options value is NULL or an Empty String
    ''' </summary>
    Private Shared ReadOnly m_Regex_DefaultOptions As RegexOptions = RegexOptions.IgnoreCase Or RegexOptions.ExplicitCapture Or RegexOptions.Multiline

    ''' <summary>
    ''' Get the regular expressions options to use by a passed string of data.
    ''' Formatted like command line arguments.
    ''' </summary>
    ''' <param name="options">options example, full or partial names can be used after slashes or hypens with or without spaces, some are exclusive of each other "/ic /ex -s" = "\ignorecase -explicitcapture/singleline "</param>
    Private Shared Function Regex_Options(options As SqlString) As RegexOptions
        Return Regex_Options(If(options.IsNull, "", options.Value))
    End Function

    ''' <summary>
    ''' Get the regular expressions options to use by a passed string of data.
    ''' Formatted like command line arguments.
    ''' </summary>
    ''' <param name="options">options example, full or partial names can be used after slashes or hypens with or without spaces, some are exclusive of each other "/ic /ex -s" = "\ignorecase -explicitcapture/singleline"</param>
    Private Shared Function Regex_Options(options As String) As RegexOptions
        'empty options string is considered default options.
        If options Is Nothing OrElse options = "" Then
            Return m_Regex_DefaultOptions
        Else
            Dim out As RegexOptions
            If m_Regex_Buffered_Options.TryGetValue(options, out) Then
                Return out
            Else
                'must build options and store them
                If options Like "*[/\-]n*" Then
                    out = RegexOptions.None
                End If
                If options Like "*[/\-]s*" Then
                    out = out Or RegexOptions.Singleline
                End If
                If options Like "*[/\-]m*" Then
                    out = out Or RegexOptions.Multiline
                End If
                If options Like "*[/\-]co*" Then
                    out = out Or RegexOptions.Compiled
                End If
                If options Like "*[/\-]c[ui]*" Then
                    out = out Or RegexOptions.CultureInvariant
                End If
                If options Like "*[/\-]ecma*" Then
                    out = out Or RegexOptions.ECMAScript
                End If
                If options Like "*[/\-]e[xc]*" Then
                    out = out Or RegexOptions.ExplicitCapture
                End If
                If options Like "*[/\-]i[c]*" OrElse options Like "*[/\-]ignorec*" Then
                    out = out Or RegexOptions.IgnoreCase
                End If
                If options Like "*[/\-]i[pw]*" OrElse options Like "*[/\-]ignore[pw]*" Then
                    out = out Or RegexOptions.IgnorePatternWhitespace
                End If
                If options Like "*[/\-]r[tl]*" Then
                    out = out Or RegexOptions.RightToLeft
                End If
                'store the options for next call (for speed)
                m_Regex_Buffered_Options(options) = out
                Return out
            End If
        End If
    End Function

End Class
于 2013-06-06T22:55:27.827 に答える