我将一个简单的DataTable序列化为XML,并将结果存储在一个字符串中。使用StringWriter和DataTable.WriteToXml,这很好。
public class Parameters
{ private DataTable ParamList = new DataTable();
public Parameters()
{ //Default constructor, build datatable with two empty columns
ParamList.TableName = "Parameter";
ParamList.Columns.Add("Name",Type.GetType("System.String"));
ParamList.Columns.Add("Value",Type.GetType("System.Object")); }
...
public string ConvertToXML()
{ string result;
using(var sw = new System.IO.StringWriter())
{ ParamList.WriteXml(sw);
result = sw.ToString();
}
return result;
}
}
这与宣传的一样。但是,在定义字段时,XML非常冗长:
<DocumentElement>
<Parameter>
<Name>ClientNumber</Name>
<Value xsi:type="xs:string" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">00001</Value>
</Parameter>
<Parameter>
<Name>FirstName</Name>
<Value xsi:type="xs:string" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">John</Value>
</Parameter>
<Parameter>
<Name>LastName</Name>
<Value xsi:type="xs:string" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">Smith</Value>
</Parameter>
...
我想在VALUE字段中删除所有命名空间和数据类型声明,就像显示NAME字段一样。我已经玩弄了XmlWriterSettings(),但似乎无法找到任何设置来实现这一目标。有什么想法吗?我建议可能吗?
(注1:我的目的只是将数据表中的字段和值记录到SQL表中,由于字段和值的数量可能不同,这似乎是最简单的方法.XML赢了读回来,所以强类型数据元素对我的目标并不重要。)
(注2:我希望在不使用RegEx的情况下实现这一目标,但如果这是我唯一的选择,那可能就是我的方向。)
查看此内容,但无法调整语法以使用DataTable。
答案 0 :(得分:1)
这是我尝试过的完整程序 - 所以Holder用于保存任何内容并序列化值:
public class Holder:IXmlSerializable
{
public object Data { get; set; }
public XmlSchema GetSchema()
{
return null;
}
public void ReadXml(XmlReader reader)
{
}
public void WriteXml(XmlWriter writer)
{
writer.WriteString(Data.ToString());
}
}
public class DataTableManager
{
public static void Save()
{
DataTable dataTable = new DataTable("table1");
DataColumn dataColumn = new DataColumn("Column1",typeof(string));
DataColumn dataColumn2 = new DataColumn("Column2",typeof(Holder));
dataTable.Columns.Add(dataColumn);
dataTable.Columns.Add(dataColumn2);
dataTable.Rows.Add("ro2", new Holder(){Data = 1});
dataTable.Rows.Add("ro3", new Holder() { Data = "Test" });
dataTable.Rows.Add("ro4", new Holder() { Data = new decimal(10) });
Debug.WriteLine(dataTable.Namespace);
//To file:
dataTable.WriteXml(@"c:\development\datatable.xml",XmlWriteMode.IgnoreSchema);
//To string
StringBuilder stringBuilder = new StringBuilder();
dataTable.WriteXml(new StringWriter(stringBuilder));
Debug.WriteLine(stringBuilder.ToString());
}
}
这将生成没有任何名称空间的xml,并将创建如上所述的三行。
答案 1 :(得分:1)
我提出了一个解决方案,但在我宣布这个答案之前,我等待更多有经验的意见。
正如我在评论中指出的那样,Namespace和Datatype声明只出现在Value字段中,因为它在DataTable声明中被强制转换为Object。这具有功能价值,所以我无法改变它。但我可以克隆表,在克隆的数据表仍然为空时更改字段的数据类型,用原始数据表中的数据填充表,然后执行我原来的相同WriteXML()。
Public class Parameters
{ private DataTable ParamList = new DataTable();
public Parameters()
{ //Default constructor, build datatable with two empty columns
ParamList.TableName = "Parameter";
ParamList.Columns.Add("Name",typeof(string));
ParamList.Columns.Add("Value",typeof(object)); }
...
public string ConvertToXML()
{ string result;
//Clone Datatable, change Object field to datatype String
var dtClone = ParamList.Clone();
dtClone.Columns["Value"].DataType = typeof(string);
ParamList.AsEnumerable().CopyToDataTable(dtClone, LoadOption.OverwriteChanges);
using(var sw = new System.IO.StringWriter())
{ dtClone.WriteXml(sw);
result = sw.ToString();
}
return result;
}
}
输出:
<DocumentElement>
<Parameter>
<Name>ClientNumber</Name>
<Value>00001</Value>
</Parameter>
<Parameter>
<Name>FirstName</Name>
<Value>John</Value>
</Parameter>
<Parameter>
<Name>LastName</Name>
<Value>Smith</Value>
</Parameter>
...
答案 2 :(得分:0)
你上面所做的实际上是Avneesh建议的(编辑前)。
如果你真的想忍受,那么继承XmlWriter。这是抽象类。要在序列化中使用它,请执行以下操作:
DataTable dt;
var myXmlSerialization = new MyXmlWriter();
dt.WriteXml(myXmlSerialization);
可以找到XmlWriter实现的示例here
我建议你不要。
答案 3 :(得分:0)
这很简单。如果你有SomeDataSet,只需将它的前缀和名称空间设置为null:
SomeDataSet.Prefix = null;
SomeDataSet.Namespace = null;
SomeDataSet.Table.WriteXml(filename);