web-dev-qa-db-ja.com

XmlSerializerが辞書をサポートしないのはなぜですか?

辞書がXmlSerializerでサポートされていない理由について興味がありますか?

DataContractSerializerを使用してXmlTextWriterにオブジェクトを書き込むことで簡単に回避できますが、XmlSerializerの処理を困難にする辞書の特徴は何ですかそれが本当にKeyValuePairsの配列だと考えると。

実際、IDictionary<TKey, TItem>を期待するメソッドにIEnumerable<KeyValuePairs<TKey, ITem>>を渡すことができます。

46
theburningmonk

ハッシュテーブルには通常、ハッシュコードと等値比較プロバイダーが必要です。これらはXMLで簡単にシリアル化できず、間違いなく移植性がありません。

しかし、あなたはすでにあなたの答えを見つけたと思います。ハッシュテーブルをList<KeyValuePair<K,V>>としてシリアル化してから、ハッシュテーブルに(再)構築します。

27
leppie

これはすぐに遅れます-しかし、私は自分で答えを探している間にこの質問を見つけ、XmlSerializerをすべてをシリアル化する別のツールに置き換える最終的な答えを共有すると思いました:

http://www.sharpserializer.com

それは、箱から出してすぐに機能し、辞書、マルチレイヤーのカスタム型、さらにインターフェースを型引数として使用するジェネリックをシリアライズしました。また、完全に許可されたライセンスを持っています。

パヴェル・イジコウスキ、ありがとう!

7
Nich Overend

ExtendedXmlSerializer を使用できます。クラスがある場合:

public class TestClass
{
    public Dictionary<int, string> Dictionary { get; set; }
}

このクラスのインスタンスを作成します。

var obj = new TestClass
{
    Dictionary = new Dictionary<int, string>
    {
        {1, "First"},
        {2, "Second"},
        {3, "Other"},
    }
};

ExtendedXmlSerializerを使用してこのオブジェクトをシリアル化できます。

var serializer = new ConfigurationContainer()
    .UseOptimizedNamespaces() //If you want to have all namespaces in root element
    .Create();

var xml = serializer.Serialize(
    new XmlWriterSettings { Indent = true }, //If you want to formated xml
    obj);

出力xmlは次のようになります。

<?xml version="1.0" encoding="utf-8"?>
<TestClass xmlns:sys="https://extendedxmlserializer.github.io/system" xmlns:exs="https://extendedxmlserializer.github.io/v2" xmlns="clr-namespace:ExtendedXmlSerializer.Samples;Assembly=ExtendedXmlSerializer.Samples">
  <Dictionary>
    <sys:Item>
      <Key>1</Key>
      <Value>First</Value>
    </sys:Item>
    <sys:Item>
      <Key>2</Key>
      <Value>Second</Value>
    </sys:Item>
    <sys:Item>
      <Key>3</Key>
      <Value>Other</Value>
    </sys:Item>
  </Dictionary>
</TestClass>

ExtendedXmlSerializerを nuget からインストールするか、次のコマンドを実行できます。

Install-Package ExtendedXmlSerializer
3
Wojtpl2