2011-03-30 48 views
0

我们正在使用XML文件来保存我们的数据都是双倍的。由于我们的数据非常庞大,因此在GB的范围内,我们将其转换为字节以节省磁盘空间和访问时间。此外,我们正在将数据写入几MB的数据块中,并且新数据块也可能来自与之前数据源相同的数据源,或者来自不同数据源。对于每个新源,我们都在XML文件中创建了一个元素,以便将来很容易地识别来自该源的数据。 我们面临的问题是,如何识别与XML文件中的源对应的元素,然后将对应于该源的数据附加到已经在XML文件中捕获的数据。我正在使用Linq XML,并无法谷歌任何解决方案使用此方法。我尝试了XMLWriter类,但是使用它的问题是如何识别或访问我想写块的元素。如何将二进制数据附加到XML文件中特定位置的特定节点

+0

究竟你的“将其转换为字节”是什么意思?这就是每个流都会做的。 – 2011-03-30 18:06:05

回答

1

对于编写大量二进制数据(由于需要将二进制数据存储为Base64字符串或其他字符安全编码)而言,XML并不是一种好的格式,也不适用于在大型数据库中更新数据块文件。我建议重新考虑你的文件格式。

如果你必须去与XML:

  • 确保您的字节数组时,写入XML
  • 你必须复制XML时要在中间插入数据base64编码。考虑使用XmlReader和XmlWriter。将源XML复制到要添加数据的位置,将数据添加到输出写入器,然后完成复制剩余部分的XML。
  • 避免在内存中加载整个XML,因为它会导致您的GB数据范围出现问题。
0

我确定我没有这里的全貌,但很难理解你为什么不使用数据库。尽管如此,跟进阿列克谢的帖子,这里是你如何使用的XmlReader和XmlWriter的来完成我觉得你想要做一个人为的例子:

//start with some dummy data 
string bigData = "<bigdata><rec id='1'>1234</rec><rec id='2'>2468</rec></bigdata>"; 
string criterion = "2"; 
string append = "10"; 
string newValue = ""; 
bool match = false; 
StringBuilder sb = new StringBuilder(); 
using (XmlWriter writer = XmlWriter.Create(sb)) 
{ 
    using (XmlReader reader = XmlReader.Create(new StringReader(bigData))) 
    { 
    while (reader.Read()) 
    { 
    switch (reader.NodeType) 
    { 
    case XmlNodeType.Element: 
     if (reader.LocalName == "rec") 
     { 
      match = reader.GetAttribute("id").ToString() == criterion; 
     } 
     writer.WriteStartElement(reader.LocalName); 
     writer.WriteAttributes(reader, true); 
     if (reader.IsEmptyElement) 
     { 
      writer.WriteEndElement(); 
     } 
     break; 
    case XmlNodeType.Text: // do the append here 
     newValue = match ? reader.Value + append : reader.Value; 
     writer.WriteString(newValue); 
     break; 
    //other cases based on node types 
    case XmlNodeType.EndElement: 
     writer.WriteFullEndElement(); 
     break; 
    }                  
    } 
     writer.Flush(); 
     string x = sb.ToString();//output 
    }       
}