Note
Access to this page requires authorization. You can try signing in or changing directories.
Access to this page requires authorization. You can try changing directories.
Question
Thursday, May 12, 2011 8:32 PM
Hi i am using the following code to query my XML file
var query = from item in xml.Root.Element("CLASS_A").Descendants("Something")
select item;
foreach (var record in query)
{
XElement my = record.Parent;
Console.WriteLine("");
Console.WriteLine("Parent name:{0}", my.Parent.Name);
Console.WriteLine("Location of record in XML :{0}", ????);> Need this
Console.WriteLine("");
}
How do i get the path of the record retrieved above so i could use it as an XPATH below
XmlDocument xml = new XmlDocument();
xml.LoadXml(str);
XmlNodeList xnList = xml.SelectNodes("Need the above record Path") << I need the recored path from above so i could use it here
Any help or suggestion would be appreciated thanks
A candle loses nothing by lighting another candle.
All replies (9)
Friday, May 13, 2011 7:30 AM ✅Answered
Hello,
using System;
using System.Text;
using System.Xml;
namespace XmlDocClassA
{
class Program
{
static void Main(string[] args)
{
const string str = @"<root>
<CLASS_A>
<Something></Something>
<someNode>
<Something></Something>
</someNode>
</CLASS_A>
</root>";
XmlDocument xmldoc = new XmlDocument();
xmldoc.LoadXml(str);
XmlNodeList list = xmldoc.SelectNodes("//CLASS_A//Something");
foreach (XmlNode record in list)
{
XmlNode myParent = record.SelectSingleNode("../..");
Console.WriteLine("");
if (myParent != null)
Console.WriteLine("Parent name : {0}", myParent.Name);
Console.WriteLine("Location of record in XML : {0}", FindXPath(record)); //> Need this
Console.WriteLine("");
}
Console.ReadKey();
}
static string FindXPath(XmlNode node)
{
StringBuilder builder = new StringBuilder();
while (node != null)
{
switch (node.NodeType)
{
case XmlNodeType.Attribute:
builder.Insert(0, "/@" + node.Name);
node = ((XmlAttribute)node).OwnerElement;
break;
case XmlNodeType.Element:
int index = FindElementIndex((XmlElement)node);
builder.Insert(0, "/" + node.Name + "[" + index + "]");
node = node.ParentNode;
break;
case XmlNodeType.Document:
return builder.ToString();
default:
throw new ArgumentException("Only elements and attributes are supported");
}
}
throw new ArgumentException("Node was not in a document");
}
static int FindElementIndex(XmlElement element)
{
XmlNode parentNode = element.ParentNode;
if (parentNode is XmlDocument)
{
return 1;
}
XmlElement parent = (XmlElement)parentNode;
int index = 1;
foreach (XmlNode candidate in parent.ChildNodes)
{
if (candidate is XmlElement && candidate.Name == element.Name)
{
if (candidate == element)
{
return index;
}
index++;
}
}
throw new ArgumentException("Couldn't find element within parent");
}
}
}
Kind regards,
Tuesday, May 17, 2011 9:11 PM ✅Answered
The xpath returned of your function does not contain attributes. It may be a problem if a node is a child of two nodes having the same name but different attribute values.
This function provides a valid xpath :
static string FindXPath(XmlNode node)
{
StringBuilder builder = new StringBuilder();
while (node != null)
{
switch (node.NodeType)
{
case XmlNodeType.Attribute:
builder.Insert(0, "/@" + node.Name);
node = ((XmlAttribute)node).OwnerElement;
break;
case XmlNodeType.Element:
int index = FindElementIndex((XmlElement)node);
builder.Insert(0, "/" + node.Name + "[" + index + "]");
node = node.ParentNode;
break;
case XmlNodeType.Document:
return builder.ToString();
default:
throw new ArgumentException("Only elements and attributes are supported");
}
}
throw new ArgumentException("Node was not in a document");
}
static int FindElementIndex(XmlElement element)
{
XmlNode parentNode = element.ParentNode;
if (parentNode is XmlDocument)
{
return 1;
}
XmlElement parent = (XmlElement)parentNode;
int index = 1;
foreach (XmlNode candidate in parent.ChildNodes)
{
if (candidate is XmlElement && candidate.Name == element.Name)
{
if (candidate == element)
{
return index;
}
index++;
}
}
throw new ArgumentException("Couldn't find element within parent");
}
Thursday, May 12, 2011 9:37 PM
Hi,
Firs you will need to retrieve all your Something nodes, XPATH :
/*/CLASS_A/*//Something
Then in a foreach loop, you can retrieve for each Something node its parent, XPATH :
..
Kind regards,
Thursday, May 12, 2011 10:24 PM
Hi,
Firs you will need to retrieve all your Something nodes, XPATH :
/*/CLASS_A/*//Something
Then in a foreach loop, you can retrieve for each Something node its parent, XPATH :
..
Kind regards,
I am not really sure what that means (sorry abt that) , could you kindly give a small code sample .. ??
A candle loses nothing by lighting another candle.
Monday, May 16, 2011 7:37 AM
Check this tutorial for more about XPath:
http://www.w3schools.com/XPath/default.asp Leo Liu [MSFT]
MSDN Community Support | Feedback to us
Get or Request Code Sample from Microsoft
Please remember to mark the replies as answers if they help and unmark them if they provide no help.
This response contains links reference to a third party World Wide Web site. Microsoft is providing this information as a convenience to you.
Microsoft does not control these sites and has not tested any software or information found on these sites; therefore, Microsoft cannot make any representations regarding the quality, safety, or suitability of any software or information found there.
There are inherent dangers in the use of any software found on the Internet, and Microsoft cautions you to make sure that you completely understand the risk before retrieving any software from the Internet.
Monday, May 16, 2011 4:57 PM
static string XPath(XElement e)
{
if (e == null)
return null;
else
return XPath(e.Parent) + "/" + e.Name;
}
Monday, May 16, 2011 5:09 PM
What about attributes and node index ?
aelassas.free.fr
Tuesday, May 17, 2011 4:55 PM
What is the question?
Wednesday, May 18, 2011 12:46 PM
You're right. Indexes are good.