- PR -

C# XML逆シリアル化について

1
投稿者投稿内容
kky
会議室デビュー日: 2008/05/13
投稿数: 2
投稿日時: 2008-05-13 13:57
初投稿及び、初心者ゆえ至らないとこがあると思いますがよろしくお願い致します。

開発環境:Visual C#(Visual Studio 2008)

質問:XMLシリアル化、逆シリアル化について
   .NETでは、オブジェクトをXMLファイルし、XMLファイルから、オブジェクトを生成すること
   もできる機能を有していると思います。
   シリアル化、逆シリアル化の際に以下の内容が可能であるかを教えていただきたいのです。

-----------------------保存対象オブジェクト--------------------------------------------
namespace test
{
[Serializable]
public class Main
{
public SubA[] sa;

public class SubA
{
public string NameA;

public SubB []sb;

public class SubB
{
public string NameB;
}
}
}
--------------------------------------------------------------------------------------

----------------------オブジェクトシリアル化------------------------------------------
<?xml version="1.0"?>
<Main xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<sa>
<SubA>
<NameA>NameA0</NameA>
<sb>
<SubB>
<NameB>NameB0</NameB>
</SubB>
<SubB>
<NameB>NameB1</NameB>
</SubB>
</sb>
</SubA>
<SubA>
<NameA>NameA1</NameA>
<sb>
<SubB>
<NameB>NameB0</NameB>
</SubB>
<SubB>
<NameB>NameB1</NameB>
</SubB>
<SubB>
<NameB>NameB2</NameB>
</SubB>
</sb>
</SubA>
</sa>
</Main>
--------------------------------------------------------------------------------------

上記のXMLファイルであれば、逆シリアル化も可能であると思うのですが、
以下の場合には、逆シリアル化はできるのでしょうか?

----------------------他のXMLファイル------------------------------------------
<?xml version="1.0"?>
<SubA>
<NameA>NameA0</NameA>
<SubB>
<NameB>NameB0</NameB>
</SubB>
<SubB>
<NameB>NameB1</NameB>
</SubB>
</SubA>
<SubA>
<NameA>NameA1</NameA>
<SubB>
<NameB>NameB0</NameB>
</SubB>
<SubB>
<NameB>NameB1</NameB>
</SubB>
<SubB>
<NameB>NameB2</NameB>
</SubB>
</SubA>
</Main>
--------------------------------------------------------------------------------------

上記のファイルでは、各インスタンスの配列に関してのタグがなくなっています。
このような場合でも逆シリアル化は可能なのでしょうか?
意図としては、他のソフトウェアのXMLフォーマットがこのようになっていたため、
逆シリアル化ができないか検討していました。

できない場合には地道に読み込む方法しかないのかと考えています...。

申し訳ありませんがよろしくお願い致します。

Hongliang
ぬし
会議室デビュー日: 2004/12/25
投稿数: 576
投稿日時: 2008-05-13 15:12
XmlElement 属性を使えば配列とフラットな XML 要素列間のシリアライズ処理に対応できます。
シリアライズする型が既存で属性を付けることができないのなら、XmlSerializer のコンストラクタで属性のオーバーライドも可能です。

個人的にはスキーマのない他の人が作った XML に対して XmlSerializer を使おうとは思いませんが。
よこけん
大ベテラン
会議室デビュー日: 2006/01/31
投稿数: 216
投稿日時: 2008-05-13 15:35
あまり詳しくないのですが、調べてみましたところ配列フィールドに XmlElementAttribute 属性を付加することで実現できました。
既定ではフィールド名が各要素の名前に使われてしまうので属性の ElementName 引数で SubA なり SubB なりを指定する必要があります。
# 配列の要素に派生型が含まれる場合は、派生型の数だけ XmlElementAttribute を付加しそれぞれの Type 引数に派生型を指定します。
# この場合、要素名に型名が使われるので、ElementName 引数は指定する必要がありません。

参考
[url=http://www.atmarkit.co.jp/fdotnet/easyxml/easyxml11/easyxml11_03.html]

_________________
C#と諸々
unibon
ぬし
会議室デビュー日: 2002/08/22
投稿数: 1532
お住まい・勤務地: 美人谷        良回答(20pt)
投稿日時: 2008-05-13 15:43
引用:

kkyさんの書き込み (2008-05-13 13:57) より:
意図としては、他のソフトウェアのXMLフォーマットがこのようになっていたため、
逆シリアル化ができないか検討していました。

できない場合には地道に読み込む方法しかないのかと考えています...。


あまり良くは知りませんが、もしほかにも問題があったりするようでしたら、いっそのこと XML のツリーを DOM レベルで API を使って手作業で整形してから、デシリアライズにまわすというやりかたもあります。こうすればどんな XML が来ても対処できます。
kky
会議室デビュー日: 2008/05/13
投稿数: 2
投稿日時: 2008-05-13 18:30
引用:

よこけんさんの書き込み (2008-05-13 15:35) より:
あまり詳しくないのですが、調べてみましたところ配列フィールドに XmlElementAttribute 属性を付加することで実現できました。
既定ではフィールド名が各要素の名前に使われてしまうので属性の ElementName 引数で SubA なり SubB なりを指定する必要があります。



Hongliangさん、よこけんさん。
その通りに動作しました。
ありがとうございました。

それのみならず、みなさんから
アドバイス、指摘をいただきありがとうございました。
1

スキルアップ/キャリアアップ(JOB@IT)