独自シリアライズ(.net)

.netで作成したアプリケーションのデータを永続的に保存するにはSystem.Runtime.Serialization.DataContractを使う。
クラスの復元に必要な属性をアノテーションで指定しておけば簡単に永続保存できる。
だが欠点がある。
シリアライズ・デシリアライズに使うJSONパーサが非常に遅いのだ。
少し大きなデータになると数十秒から数百秒のオーダーとなってしまうことはザラだ。
また参照オブジェクトの保存ができないので、いわゆるアドレス参照の属性を保存するには、それなりのロジック拡張が必要となる。

このあたりを解消する独自パーサを作ってみた。
ネイティブな型は以下の通り。
Byte,Char,Short,Integer,Long,Single,Double,String,Boolean,
Date,Enum,Array,List,Dictionary,
System.Drawing.Point,System.Drawing.Color
これ以外はDataContract指定のクラスでまかなう必要がある。

使い方はこんな感じになるだろうか。
Byson.BysonStorageがパーサで第一引数はマジックNo(ファイルを特定するためのLong番号)、第二引数はパーサがクラスを生成するために必要なアセンブリを渡している。
マジックNoはアプリケーション毎に違う番号にする必要がある。
IsMyFileはマジックNoによりファイルを識別している。
AnyObjectがDataContractにより定義されているクラスで、下記例ではひとつだが、ネイティブ型さえ使えば、あらゆるクラスがシリアライズ可能である。
認識可能と判断されたファイルからReadし、何らかの編集後、Writeにて永続化している。

<System.Runtime.Serialization.DataContract()>
Public Class AnyObject
  <System.Runtime.Serialization.DataMember()>
  Private _data As String
  Public Sub New()
  End Sub
  Public ReadOnly Property Data As String
    Get
      Return Me._data
    End Get
  End Property
End Class
Public Class Mainclass
  Public Shared Sub Main()
    Dim storage As New Byson.BysonStorage(
      123456789L,
      System.Reflection.Assembly.GetExecutingAssembly()
    )
    Dim path As String = "c:hogedata.dat"
    If storage.IsMyFile(path) Then
      Dim anyobject = storage.Read(path)
      '
      ' edit anyobject ...
      '
      storage.Write(path, anyobject)
    Else
      MessageBox.Show("It is not my file !", "byson",
                      MessageBoxButtons.OK,
                      MessageBoxIcon.Warning)
    End If
  End Sub
End Class

サンプル付きのプロジェクトを公開しますので、興味のある方は遊んでみてください。
サンプル付きプロジェクトはこちら

コメントを残す

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です