Modify an XML file in place?

Suppose I have the following XML file:

<book> <name>sometext</name> <name>sometext</name> <name>sometext</name> <name>Dometext</name> <name>sometext</name> </book> 

If I wanted to change the contents by changing D to s (as shown in the fourth "name" node) without having to read / write the whole file, is this possible?

+4
source share
4 answers

A file with 10 MB is not a problem. Bear it. Change the DOM. Write it back to the file system. 10 GB is a big problem. In this case:

Guess You do not change the file length. Think of the file as an array of characters, not a (linked) list of characters: you cannot add characters in the middle, but only change them.

You need to seek to change the position in the file, and then write to a character.

In the .NET world with a FileStream object, you must set the Position attribute to the index of the D character, and then write a single s character. Check this question for random access to text files .

Also read this question: How to insert characters into a file using C # . It sounds like you can't use a FileStream object, but instead you have to resort to writing individual bytes.

Good luck. But actually, if we are only talking about 10 MB, then just break it. The computer should do your work.

+3
source

I would just read in the file, process and return it back.

This can be done in a streaming way with XmlReader - it is more manual than XmlDocument or XDocument, but it does not allow creating DOM memory in memory (XmlDocument / XDocument can be used with the same read / write pattern, but usually requires a complete reconstruction in memory) :

  • Open file stream input file (XmlReader)
  • Open stream of output files (XmlWriter, to another file)
  • Reading from XmlReader and writing to XmlWriter, performing any conversion as necessary.
  • Close streams
  • Move new file to old file (overwrite, atomic action)

While this can be configured to handle input and output in the same open file with a bunch of really smart work, nothing will be saved, and there will be many cases with an edge, including an increase with decreasing file length. In fact, it might be slower to just try moving the contents of the file back to fill in the blanks or moving the contents of the file forward to create a new room. The file system cache is likely to make any "winnings" minimal / controversial for anything but the most basic length-saving operation. In addition, changing the file in place is not an atomic action and, as a rule, is not restored in case of an error: due to the temporary file, the read / write / move approach is atomic in the final contents of the file.

Or, consider XSLT - it was designed for that; -)

Happy coding.

+2
source

The cleanest (and best) way is to use the XmlDocument object for management, but the quick and dirty solution is to simply read the XML for the string, and then:

 xmlText = xmlText.Replace("Dometext", "sometext"); 
+1
source

The XML file is a text file and does not allow insertion / deletion. The only mutations supported are OverWrite and Append. Not suitable for XML.

So first make sure you really need it. This is a complex operation, it only costs on very large files.

Since there may be a change in length, you will at least have to move everything after the first replacement. The possibility of multiple substitutions means that you may need a large buffer to make changes.

It’s easier to copy the whole file. It's expensive in I / O, but you save memory usage.

+1
source

All Articles