首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >从数据库中导出XML文件,并在实际列之前获得没有任何属性的干净格式

从数据库中导出XML文件,并在实际列之前获得没有任何属性的干净格式
EN

Stack Overflow用户
提问于 2020-01-07 04:27:09
回答 1查看 75关注 0票数 0

我正在创建一个服务,该服务将使用WriteXml从用户存储过程中生成并导出来自sql server db的xml文件。它可以成功运行,但是我不希望输出的xml文件在我想要的实际列之前包含任何xml属性。我试过IgnoreSchema。但是第一行xml版本仍然存在,我试图在列之间添加空格。

代码:

代码语言:javascript
运行
复制
public void TEST(string param)
{    
     List<Model> list = new List<Model>();

     //this function is for access the db and get the data
     DataSet ds = DAL.Function(param);

     //Export as XML File
     //ds.WriteXml(@"C:\Test\Test.XML", XmlWriteMode.WriteSchema);
}

输出如下所示:

代码语言:javascript
运行
复制
<?xml version = "1.0" standalone="yes"?>
<NewDataSet>
  <Table>
    <a> 005 </a>
    <b> 1 </b>
  </Table>
  <Table>
    <a> 006 </a>
    <b> 2 </b>
  </Table>
</NewDataSet>

但我希望它看起来像这样的格式化:

代码语言:javascript
运行
复制
  <Table>
    <a> 005 </a>
    <b> 1 </b>
  </Table>

  <Table>
    <a> 006 </a>
    <b> 2 </b>
  </Table>
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2020-01-07 06:42:30

首先,我要指出格式良好的XML文档必须有only one root element

在正常情况下,我会说您不应该尝试弄乱System.Xml名称空间,因为它会变得非常脏。但让我们再想象一下,我们并不关心性能和可维护性,当然,这纯粹是一个思想实验。然后,解决问题的一种方法是修改XmlWriter,使其跳过您的NewDataSet标记:

代码语言:javascript
运行
复制
class MyWriter : XmlTextWriter
{
    private int Top // this is a pointer to top of internal stack that XmlWriter uses to determine closing tag correspondence
    {
        get
        {
            FieldInfo top = typeof(XmlTextWriter).GetField("top", BindingFlags.NonPublic | BindingFlags.Instance);
            return (int)top.GetValue(this);
        }
    }

    public MyWriter(string name, Encoding enc) : base(name, enc) {}

    public override void WriteStartElement(string prefix, string localName, string ns)
    {
        if (localName == "NewDataSet") { // skip the tag
            MethodInfo PushStack = typeof(XmlTextWriter).GetMethod("PushStack", BindingFlags.NonPublic | BindingFlags.Instance);
            PushStack.Invoke(this, new object[] {}); // for internal state tracking to work, we still need to push the stack as if we wrote it out. we'll have to account for that later
            return;
        }

        base.WriteStartElement(prefix, localName, ns);
    }

    public override void WriteEndElement()
    {
        if(Top <= 1) return; // do not attempt to write outermost tag, we already skipped it in the opening counterpart
        base.WriteEndElement();
    }
}
void Main()
{
    //...your code here

    var writer = new MyWriter(@"C:\Test\Test.XML", Encoding.UTF8); // instantiate your own writerm
    ds.WriteXml(writer, XmlWriteMode.IgnoreSchema); // and use it instead of stock standard
}

正如您所看到的,问题是,XmlWriter没有公开一些工作所需的方法和属性,所以我不得不使用反射来调用它们。此外,通过将某些数据结构放在类内部来获取它们变得极其困难(作为练习,请尝试使用上面的技术获取TagInfo[] stack字段,看看会发生什么情况)。

然而,这应该会给你想要的输出。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/59618521

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档