XmlNodeList.XQL returns 2 results while I was expecting just 1

I have a problem with the XmlNodeList.XQL method on both RS 2012r2.1 and Xojo 2013r2

To make an example, imagine that I have this XML code:

<movies>
    <movie>
        <title>
            Casablanca
        </title>
    </movie>
    <movie>
        <title>
            Gone with the wind
        </title>
    </movie>
</movies>

I’d like to get the title of the first movie. So I decide to query the XML code to get the first node in by using the XQL method; then, I’d like to take that first element and make another query on it to get the first node named that appears inside of it.

When I do this, the first query correctly gives me back this list:

1) <movie><title>Casablanca</title></movie>
2) <movie><title>Gone with the wind</title></movie>

Then, I take the first item from that list, that is:

<movie><title>Casablanca</title></movie>

And I make another query on it to get a list of every element named that are nested inside. I’d expect to get just one item, but instead I’m getting two of them:

1) <title>Casablanca</title>
2) <title>Gone with the wind</title>

The first item is as expected (Casablanca), but the second item (Gone with the wind) doesn’t belong to the node I just queried.
Since I’m doing a query on a specific node and not on the entire node, I wasn’t expecting it.

It’s driving me mad, so I really need to ask you the favor of telling me if you see any flaw in the source code I wrote below.
Is this a bug? Or do I have written something wrong?

This is the complete source code I wrote:


Dim source As String = "<movies>" _
+ "<movie><title>Casablanca</title></movie>" _
+ "<movie><title>Gone with the wind</title></movie>" _
+ "</movies>"

Dim xmlSource As XmlDocument = New XmlDocument()
xmlSource.LoadXml(source)

Dim movieList As XmlNodeList = xmlSource.Xql("//movie")

Dim firstMovie As XmlNode = movieList.Item(0)

' firstMovie contains:
'
' <movie><title>Casablanca</title></movie>

' Now, the following line is important:
'
' -----------------------------------------------

Dim theTitleElement As XmlNodeList = firstMovie.Xql("//title")

' -----------------------------------------------
'
Dim title As XmlNode
Dim output As String = ""
Dim nInd As Integer = 0

While (nInd < theTitleElement.Length)
  title = theTitleElement.Item(nInd)
  output = output + title.ToString + EndOfLine
  nInd = nInd + 1
Wend

MsgBox(output)

' This outputs:
'
' <title>Casablanca</title>
' <title>Gone with the wind</title>

when you write firstMovie.Xql("//title") you are asking for all the title elements in the document.

if you want the “title” elements that are direct child of the current element you have to use: firstMovie.Xql(“title”)

[quote=33817:@Antonio Rinaldi]when you write firstMovie.Xql("//title") you are asking for all the title elements in the document.
if you want the “title” elements that are direct child of the current element you have to use: firstMovie.Xql(“title”)[/quote]

Thanks for the reply.
Changing the second query from “//title” to “title” as you suggested makes the code working, but I’m still not convinced that this is the best solution to this problem, because the subject of the second XQL query is a node with a single movie, not the entire movie list. IMHO since I’m querying firstMovie and not movieList, in this context the query “//title” should indicate that I want each element in firstMovie starting from the “relative” root element ( in my example).

From my point of view, for example if I ask you the question “What’s your age?” and I affirm clearly that the subject of my question is you, I’m not expecting an answer from anybody but you.

it’s the xpath syntax
“//node” means every “node” in the document
so is checked against “firstMovie” OwnerDocument.

“node” means every “node” element that is direct child of the current element.

“//…” Will always search from the document root; that’s what the first “/” stand’s for - the root. If you want to start the search at the element on which you are executing the search, use “./” to keep the syntax analogous to “//”, or, do it as Antonio suggests.

I’ll do that for sure, but I still think that this makes no sense. When I query a node for items, I strongly believe that I should only get the items that are nested in that node as the result; when I query for elements starting from the root node, IMHO the root node should be the relative root node.

No Francesco, there are many cases where you need a global searcher.
The xPath syntax is written for all the various cases.

I’ve just finished a work where the use of the // shortcut to search collateral info let me wrote a lot less code than the “direct” way.

Nodes do not exist in isolation from a document root. That concept is foreign to XQL. While you may have a node that points to a “fragment” of the document, it is still part of the document and is treated as such.

All right. In any case the most important thing was to fix the behaviour of my code.

Thank you very much to everybody for having answered my question and for the explanations.