score:1

i think better approach would be to Deserialize XML to C# Classes and then use LINQ on that, should be fast.

score:0

If it really takes this long to run this, then maybe do something like this:

  1. Don't iterate both - only iterate the XML-File and load the Data from your DataLst (make a SQL-command or simple linq-statement to load the data based on Name/Store/Section), make a simple struct/class for your key with this data (Name/Store/Section) - don't forget to implement equals, and GetHashCode
  2. iterate through your XML-Elements and use the dictionary to find the values to replace

This way you will only iterate the XML-File once not once for every data in your DataSource.

score:2

It looks like you have an O(n)×O(m) issue here, for n = size of DataList and m = size of the xml. To make this O(n)+O(m), you should index the data; for example:

var lookup = elements.ToLookup(
       x => new {
            Name = x.Name.LocalName,
            Store = x.Element(XName.Get("Store", "")).Value,
            Section =  x.Element(XName.Get("Section", "")).Value},
       x =>  x.Element(XName.Get("Val", ""))
    );

foreach (DataSource Data in DataLst)
{ 
    XElement xmlElem = lookup[
          new {Data.Name, Data.Store, Data.Section}].Single();
    xmlElem.ReplaceWith(new XElement(XName.Get("Val", ""), Data.Value));
}

(untested - to show general approach only)

score:0

It's not clear why it's taking that long - that's a very long time. How many elements are in DataLst? I would rewrite the query for simplicity to start with though:

IEnumerable<XElement> elements = xmlDoc.Descendants();
foreach (DataSource data in DataLst)
{ 
    XElement valElement = (from element in xmlDoc.Descendants(data.Name)
                           where data.Store == element.Element("Store").Value
                              && data.Section == element.Element("Section").Value
                           select element.Element("Val")).Single();

    valElement.ReplaceWith(new XElement("Val"), data.Value));
} 

(I'm assuming none of your elements actually have namespaces, by the way.)

Next up: consider replacing the contents of valElement instead of replacing the element itself. Change it to:

valElement.ReplaceAll(data.Value);

Now, this has all been trying to keep to the simplicity of avoiding precomputation etc... because it sounds like it shouldn't take this long. However, you may need to build lookups as Marc and Carsten suggested.

score:0

Try by replacing Single() call in the LINQ with First().

score:0

At the risk of flaming, have you considered writing this in XQuery instead? There's a good chance that a decent XQuery processor would have a join optimiser that handles this query efficiently.

score:0

"Well thanks everyone for your precious time and effort"

Problem answer: Actually the object 'DataLst' was of the type IEnumerable<> which was taking time in obtaining the values but after I changed it to the List<> type the performance improved drastically (now running in 20 seconds)


Related Articles