DataContractSerializer не предназначен для управления выходом. Он разработан, чтобы быть быстрым, неявным и простым для присвоения класса.
То, что вы хотите, это XmlSerializer. Это дает вам гораздо больший контроль над выводом XML.
Обратите внимание, что в моем примере ниже я указал много вещей, которые могли бы быть выведены из имен свойств, но просто чтобы дать вам ощущение, что вы можете переопределить их в атрибутах. Фактически, я думаю, что весь этот класс мог бы сериализоваться очень хорошо, если бы все атрибуты были удалены и некоторые KnownTypeAttributes были применены, но я не проверял это. Я не знаю, даст ли это вам точный XML-код, который вы описали (он создаст корневой элемент над дочерними элементами), но, надеюсь, это направит вас в правильном направлении.
Атрибуты, управляющие сериализацией XML
[XmlRoot(Namespace="")]
public class MyClass {
[XmlArray("Children")]
[XmlArrayItem("ConcreteTypeA", typeof(ConcreteTypeA))]
[XmlArrayItem("ConcreteTypeB", typeof(ConcreteTypeB))]
public BaseType[] Children {
get;
set;
}
}
public class BaseType {
}
public class ConcreteTypeA : BaseType {
}
public class ConcreteTypeB : BaseType {
}
РЕДАКТИРОВАТЬ: Я только что проверил, и он производит что-то очень близко к тому, что вы искали.
void Main()
{
var mc = new MyClass();
mc.Children = new BaseType[] {
new ConcreteTypeA(),
new ConcreteTypeB(),
new ConcreteTypeA(),
new ConcreteTypeB()
};
var serializer = new XmlSerializer(typeof(MyClass));
using ( var str = new StringWriter() ) {
serializer.Serialize(str, mc);
str.ToString().Dump();
}
}
... производит ... (ненужные xmlns удалены с вершины)
<MyClass>
<Children>
<ConcreteTypeA />
<ConcreteTypeB />
<ConcreteTypeA />
<ConcreteTypeB />
</Children>
</MyClass>