VB.NET Tips - INIファイル読み書き処理

INIファイルというと今更感がありますが、 簡単にプログラムの動作パラメータなどを保存しておくには便利な機能です。 私もプログラムの変更なしに、外からタイミングの時間の値を後から少し変えたい場合によく使います。

INIファイルの構造は以下の様になります。

[SECTION1]
KEY1=keydata1
KEY2=keydata2

[SECTION2]
KEYA=keydataA
...
■セクション
[] で囲まれた部分がセクションで、各セクションの中にキー文字列を宣言します。

■キー
各セクションの中に宣言される文字列で、その値を = で定義します。
セクションが異なれば、同じキーが在ってもOKです。

■コメント
先頭に ;(セミコロン) を置くとその行はコメント行とみなされます。
また、行の途中に ;(セミコロン) が在ると、それ以降はコメントであるとみなされます。

■エスケープシーケンス
キーの値の文字列として ;(セミコロン) :(コロン) =(等号) #(シャープ)  の各文字を含めたい場合があります。その時には各文字の前に \(円マーク) を置きエスケープしてやります。
(以下のソースのクラスではエスケープシーケンスの設定と解除を関数化しています)

以下にINIファイルを取り扱うクラスのソースを示します。

INIファイル読み書きクラス

Public Class ClsIni
    'プロファイル文字列取得
    Private Declare Function GetPrivateProfileString Lib "kernel32" Alias "GetPrivateProfileStringA" ( _
       ByVal lpApplicationName As String, _
       ByVal lpKeyName As String, _
       ByVal lpDefault As String, _
       ByVal lpReturnedString As System.Text.StringBuilder, _
       ByVal nSize As UInt32, _
       ByVal lpFileName As String) As UInt32

    'プロファイル文字列書込み
    Private Declare Function WritePrivateProfileString Lib "kernel32" Alias "WritePrivateProfileStringA" ( _
        ByVal lpAppName As String, _
        ByVal lpKeyName As String, _
        ByVal lpString As String, _
        ByVal lpFileName As String) As Integer

    Private strIniFileName As String = ""

    ''' 
    ''' コンストラクタ
    ''' 
    ''' INIファイル名(フルパス)
    Sub New(ByVal strIniFile As String)
        Me.strIniFileName = strIniFile  'ファイル名退避
    End Sub

    ''' 
    ''' プロファイル文字列取得
    ''' 
    ''' アプリケーション文字列
    ''' キー文字列
    ''' デフォルト文字列
    ''' プロファイル文字列
    Public Function GetProfileString(ByVal strAppName As String, _
                                     ByVal strKeyName As String, _
                                     ByVal strDefault As String) As String
        Try
            Dim strWork As System.Text.StringBuilder = New System.Text.StringBuilder(1024)
            Dim intRet As Integer = GetPrivateProfileString(strAppName, strKeyName, strDefault, strWork, strWork.Capacity - 1, strIniFileName)
            If intRet > 0 Then
                'エスケープ文字を解除して返す
                Return ResetEscape(strWork.ToString())
            Else
                Return strDefault
            End If
        Catch ex As Exception
            Return strDefault
        End Try
    End Function

    ''' 
    ''' プロファイル文字列設定
    ''' 
    ''' アプリケーション文字列
    ''' キー文字列
    ''' 設定文字列
    ''' True:正常, False:エラー
    Public Function WriteProfileString(ByVal strAppName As String, _
                                       ByVal strKeyName As String, _
                                       ByVal strSet As String) As Boolean
        Try
            'エスケープ文字変換
            Dim strCnv As String = SetEscape(strSet)
            Dim intRet As Integer = WritePrivateProfileString(strAppName, strKeyName, strCnv, strIniFileName)
            If intRet > 0 Then
                Return True
            Else
                Return False
            End If
        Catch ex As Exception
            Return False
        End Try
    End Function

    ''' 
    ''' エスケープ文字変換
    ''' 
    ''' 設定文字列
    ''' 変換後文字列
    Private Function SetEscape(ByVal strSet As String) As String
        Dim strEscape As String = ";#=:"
        Dim strRet As String = strSet
        Try
            For i = 0 To strEscape.Length - 1
                Dim str As String = strEscape.Substring(i, 1)
                strRet = strRet.Replace(str, "\" & str)
            Next
            Return strRet
        Catch ex As Exception
            Return ""
        End Try
    End Function

    ''' 
    ''' エスケープ文字解除
    ''' 
    ''' 設定文字列
    ''' 変換後文字列
    Private Function ResetEscape(ByVal strSet As String) As String
        Dim strEscape As String = ";#=:"
        Dim strRet As String = strSet
        Try
            For i = 0 To strEscape.Length - 1
                Dim str As String = strEscape.Substring(i, 1)
                strRet = strRet.Replace("\" & str, str)
            Next
            Return strRet
        Catch ex As Exception
            Return ""
        End Try
    End Function
End Class

このクラスを利用する例を以下に記します。 このボタン処理内では、最初にINIファイルへの書き込みを行い、その後でそのINIファイルからの読込を行っています。
    Private Sub ButtonIni_Click(sender As Object, e As EventArgs) Handles ButtonIni.Click
        '自分自身の存在するフォルダ
        Dim strPath As String = System.IO.Path.GetDirectoryName(Application.ExecutablePath)
        'INIファイルクラスの生成
        Dim Ini As New ClsIni(strPath & "\TEST.INI")
        'INIファイルへの書込みテスト
        Ini.WriteProfileString("SECTION1", "DATA1", "test-data-1:aaa")
        Ini.WriteProfileString("SECTION1", "DATA2", "test-data-2;bbb")
        Ini.WriteProfileString("SECTION2", "DATA1", "TEST-DATA-1=:;#AAA")

        'INIファイルからの取得テスト
        Dim str As String
        str = Ini.GetProfileString("SECTION1", "DATA1", "default-data-1:aaa")
        Console.WriteLine("SECTION1:DATA1=" & str)
        str = Ini.GetProfileString("SECTION1", "DATA2", "default-data-2;bbb")
        Console.WriteLine("SECTION1:DATA2=" & str)
        str = Ini.GetProfileString("SECTION2", "DATA1", "default-DATA-1=:;#AAA")
        Console.WriteLine("SECTION2:DATA1=" & str)
        str = Console.ReadLine()
    End Sub
INIファイルへの書込みでエスケープしないといけない文字を含んでいますので、 このプログラムを実行し「TEST.INI」をテキストエディタで確認すると、  \(円マーク) が付加されて書き込まれているのがわかるはずです。