更新日:、 作成日:

VBA Mid 関数:文字列の途中から抽出する

はじめに

Excel VBA マクロの Mid 関数から文字列の途中から抽出する方法を紹介します。

Mid 関数は、文字列の指定した位置から文字数分の文字列を取得します。

123456 から 34 などを返します。

123[456]789 から [] で囲まれた 456 なども抽出できます。

文字列の途中から切り出したいときに使用します。

文字列をバイトデータとして扱うには MidB 関数を使用します。
文字列の先頭から抽出するには「Left 関数」を使用します。
文字列の途中から抽出するには「Mid 関数」を使用します。
文字列を抽出するには「文字列を抽出する」をご覧ください。

Mid 関数の引数と戻り値

Mid(文字列, 開始位置)
文字列開始位置から最後の文字まで抽出します。

Mid(文字列, 開始位置, 文字数)
抽出する文字数を指定できます。

引数「文字列」抽出元の文字列を指定します。
引数「開始位置」何文字目から抽出するかを指定します。
引数「文字数」省略できます。引数「開始位置」から抽出する文字数を指定します。
戻り値の型文字列型 (String)

解説

引数「開始位置」が 1 なら先頭の文字から抽出します。

引数「開始位置」が引数「文字列」を超えるときは、空文字 "" を返します。

引数「開始位置」が 0 や 負の値のときは「エラー 5 プロシージャの呼び出し、または引数が不正です。」が発生します。

引数「文字数」を省略したときは、引数「開始位置」から最後の文字までを返します。

引数「文字数」が 0 なら、空文字 "" を返します。

引数「文字数」が引数「文字列」を超えるときは、引数「開始位置」から最後の文字までを返します。

Unicode のサロゲートペア文字 𩸽😃 は 2 文字として扱います。これを 1 文字として取得したいときは、関数を作成します。

Len 関数」から文字数を取得して、2 文字目から最後の 3 文字目までのように抽出できます。

InStr 関数」から文字を検索して、123[456]789 から [] で囲まれた 456 を抽出できます。

使用例

Mid 関数の使用例を紹介します。

文字列の途中から抽出する

文字列の途中から抽出します。

Dim s As String
s = Mid("123456", 1)
Debug.Print(s) ' 123456

s = Mid("123456", 7)
Debug.Print(s) ' ""

s = Mid("123456", 3, 2) ' 3 文字目から 2 文字取得
Debug.Print(s) ' 34

s = Mid("123456", 3, 0) 
Debug.Print(s) ' ""

s = Mid("123456", 3, 9)
Debug.Print(s) ' 3456

文字列を抽出する

Left 関数」や「Right 関数」を使用して、先頭や最後から抽出できます。

Dim s As String

s = Left("123456", 3)   ' 左から 3 文字
Debug.Print(s) ' 123

s = Mid("123456", 2, 3) ' 2 文字目から 3 文字
Debug.Print(s) ' 234

s = Right("123456", 3)  ' 右から 3 文字
Debug.Print(s) ' 456

先頭と末尾からの文字を抽出する

Len 関数」を使用して文字数を取得し、2 文字目から最後の 3 文字目までのように抽出できます。引数が複雑なので関数を作成します。

Sub 実行()
    Dim s As String
    
    s = LeftRight("123456789", 2, 3) ' 左から 2 文字、右から 3 文字まで
    Debug.Print(s) ' 234567
    
    s = LeftRight("123456789", 3, 4) ' 左から 3 文字、右から 4 文字まで
    Debug.Print(s) ' 3456
End Sub

' 先頭と末尾の位置を指定して抽出します。
Function LeftRight(ByVal text As String, ByVal startLength As Long, ByVal endLength As Long) As String

    LeftRight = Mid(text, startLength, Len(text) - endLength - startLength + 2)
    
End Function

範囲内の文字を抽出する

InStr 関数」を使用して、特定の文字で囲まれた文字を抽出できます。引数が複雑なので関数を作成します。

Sub 実行()
    Dim s As String
    
    s = MidEnclosed("123[456]789", "[", "]") ' [ ] で囲まれた範囲
    Debug.Print(s) ' 456
    
    s = MidEnclosed("12(34567)89", "(", ")") ' ( ) で囲まれた範囲
    Debug.Print(s) ' 34567
End Sub

' 囲まれた範囲内の文字を抽出します。
Function MidEnclosed(ByVal text As String, ByVal startChar As String, ByVal endChar As String) As String
    Dim l As Long
    Dim r As Long
    l = InStr(text, startChar)
    r = InStrRev(text, endChar)

    MidEnclosed = Mid(text, l + 1, r - l - 1)
End Function

サロゲートペア文字を 1 文字として抽出する

サロゲートペア文字を 1 文字として取得するために、MidSurrogate 関数を作成して抽出しています。

サロゲートペア文字を判定する IsSurrogate 関数を使用しています。詳しくは「文字コードを変換や判定する」をご覧ください。
Sub 実行()
    Dim s As String
    s = "12" & WorksheetFunction.Unichar(171581) & "56" ' 12𩸽56

    Range("A1").Value = Mid(s, 4)             ' ?56、サロゲートペア文字の 1 文字だけ抽出するので文字化け
    Range("B1").Value = MidSurrogate(s, 4)    ' 56

    Range("A2").Value = Mid(s, 1, 4)          ' 12𩸽
    Range("B2").Value = MidSurrogate(s, 1, 4) ' 12𩸽5
End Sub

' サロゲートペア文字を 1 文字として文字を抽出します。
Function MidSurrogate(ByVal text As String, ByVal start As Long, Optional ByVal length As Long = 2147483647) As String

    Dim s As String ' 抽出した文字
    Dim char As String
    Dim index As Long ' 開始位置
    Dim midCount As Long ' 抽出した文字数

    ' 文字数を数える
    Dim i As Long
    For i = 1 To Len(text)
        index = index + 1

        ' 開始位置
        If index >= start Then
            char = Mid(text, i, 1)

            If IsSurrogate(Mid(text, i)) Then
                ' サロゲートペア文字
                char = Mid(text, i, 2)
                i = i + 1
            End If

            s = s & char

            ' 抽出文字数に達した
            midCount = midCount + 1
            If midCount >= length Then
                MidSurrogate = s
                Exit Function
            End If

        End If

    Next

    MidSurrogate = s
End Function