Dictionary型を使って簡単にConfigっぽいものを扱う

生きてます。(生存戦略報告)
Advent Calenderネタを書いたのがちょうど一年前。筆無精しまくっててだいぶご無沙汰になってしまいました。

今回はDictionary型を使ってConfigっぽいものを手軽に扱ってみようというネタです。
設定ファイルを扱う方法は、.configだったり、.iniだったり、レジストリだったり、いろいろ方法ありますが、とりあえずDictionary型を使って読み書きしてみます。
Dictionary型って、いわゆるハッシュテーブルとか連想配列って呼ばれるやつですね。

#えっと、今まで(VB.NETを触りだして10年以上)こんな型があるなんて知らなかったことを正直に白状しておきます。

たとえば、こんな感じの設定ファイル(config.txt)があったとして

data=abc
pos_x=120
pos_y=240

その設定ファイルを読み込むには、たとえばこんな読み込み用関数を作っておいて

Dim config As New Dictionary(Of String, String) 
Dim configDelimiter As Char = "="c  ' configなファイルの区切り文字

Function ReadConfig(filename As String) As Dictionary(Of String, String)
    'configファイルの読み込み
    Dim configLines As String() = IO.File.ReadAllLines(filename)

    Dim dict As New Dictionary(Of String, String)

    '読み込んだconfigのDictionary型への追加
    For Each configLine As String In configLines
        dict.Add(configLine.Split(configDelimiter)(0).Trim(" "c), configLine.Split(configDelimiter)(1).Trim(" "c))
    Next

    Return dict
End Function

読み込んであげると楽です

config = ReadConfig("Config.txt")

読み込んだデータは、For Each で取り出すことも出来ます。取り出されたのはKeyValuePair型になるっぽい。

'Configの列挙
For Each kvp As KeyValuePair(Of String, String) In config
    Console.WriteLine("{0} - {1}", kvp.Key, kvp.Value)
Next

値の追加とか

config.Add("Today", Today.ToShortDateString)
config.Add("Now", Now.ToString)

Keyが存在しているのにValueをAddしようとすると、例外を吐くので、Addする前はContainsKey(keyname)で、存在チェックをしてから更新したり追加したりするといいと思います。

If config.ContainsKey("Now") Then
    config("Now") = Now.ToString
Else
    config.Add("Now", Now.ToString)
End If

値の取得は config("pos_x") みたいな感じで取得可能です。あ、今回の例では New Dictionary(of String,String) で初期化しているので、必要あればParseしたりしてください。

また、逆に設定ファイルへの書き込みは、こんな関数を作っておいて

Sub WriteConfig(filename As String, config As Dictionary(Of String, String))
    Dim writeData As String = ""
    For Each kvp As KeyValuePair(Of String, String) In config
        writeData &= kvp.Key & configDelimiter  & kvp.Value & vbCrLf
    Next

    IO.File.WriteAllText(filename, writeData)
End Sub

書き込んであげるといいと思います。

WriteConfig("OutConfig.txt", config)

自分自身のアセンブリをSHA256とかでハッシュ取って保存しておき、実行時に検証する、っていうアセンブリの簡単な改ざんチェックとか、いろいろ用法あると思います。(今回のDictionary型じゃなくて.configとかでもできそうだけど)

例によって(?)上記サンプルでは例外対策とか、読み込み時にデリミタ文字が複数出てきたときの対処とか、全くしてないので必要あればTryしてCatchしてFinallyしたりしてみてください。