If you don't know (or care) about the full path from the root node to the node (or nodes) for which you are searching, use the double-dot operator to indicate that you want to locate all matching nodes at any level in the XML tree. For example, the following returns all <vegetable> nodes regardless of where they are in the hierarchy:
var vegetableList:XMLList = foodgroup..vegetable;
An asterisk (* ) is a wildcard for "any node." For example, the following E4X expression returns assigns to servings an XMLList containing all <servings> element nodes that are children of any nodes that are, in turn, children of the <foodgroup> node:
var servings:XMLList = foodgroup.*.servings;
The @ sign is used to signify an attribute. The following example generates an XMLList containing the values of the color attributes for the <fruit> nodes:
var colorValues:XMLList = foodgroup.fruits.fruit.@color;
Now let's look at predicate filtering. Predicate filtering uses the syntax .( condition ) to pick out element nodes that meet the condition specified. The condition is specified via a Boolean expression. The filtering acts on the XML or XMLList object that precedes the predicate filter expression.
For example, let's say you want to pick out all of the <fruit> element nodes where the color attribute is red . This can be accomplished by first generating an XMLList of all of the <fruit> element nodes using E4X dot-down syntax, and then filtering with the Boolean expression @color == "red" :
/* Displays:
<fruit color="red">Apple</fruit>
<fruit color="red">Watermelon</fruit>
*/
trace( foodgroup..fruit.( @color == "red" ) );
In this example, two things are happening in the expression passed to the TRace statement:
-
The foodgroups..fruit portion returns an XMLList of all of the <fruit> element nodes that appear in the XML tree.
-
Predicate filtering is applied on the XMLList of <fruit> nodes and a new XMLList is created that contains only those <fruit> elements matching the filtering expression, in this case, the elements with color attributes equal to red . You can see that both of the fruit element nodes with red as the value of the color attribute appear in the TRace output.
The preceding example selected the red <fruit> element nodes, but what if we wanted to select any node that had red as the value for the color attribute? Use the asterisk to look for any node, along with a predicate filter that looks for the existence of a color attribute, and if the color attribute exists, checks to make sure its value is red :
/* Displays:
<fruit color="red">Apple</fruit>
<fruit color="red">Watermelon</fruit>
<vegetable color="red">Tomato</vegetable>
*/
trace( foodgroup..*.( hasOwnProperty( "@color" ) && @color == "red" ) );
The Boolean expression used as the condition can be any expression that results in a Boolean true or false value. In the preceding example, hasOwnProperty checks to make sure the element has an attribute for color , and if so tests the value of the color attribute to see if its value is red . Only when the condition evaluates to true is the element added to the XMLList that the E4X expression returns.
So far, predicate filtering has only been done with attributes; however, it can also be used to specify that a certain element node needs to have a particular text node as a value. This is particularly useful when you have an XML document that has repeated element nodes that contain child nodes. For example, here is how to display the value of the color attribute for whichever <fruit> element node has a <name> element node with a text node value of Apple :
var fruits:XML = <fruits>
<fruit color="red">
<name>Apple</name>
</fruit>
<fruit color="orange">
<name>Orange</name>
</fruit>
<fruit color="green">
<name>Pear</name>
</fruit>
<fruit color="red">
<name>Watermelon</name>
</fruit>
</fruits>;
// Displays: red
trace( fruits.fruit.(name == "Apple").@color );
As you can see, predicate filtering is quite powerful, and it gets even more powerful when combined with regular expressions. The following example uses a regular expression to find all of the <fruit> element nodes that have a <name> child node containing a text node starting with a vowel:
var fruits:XML = <fruits>
<fruit color="red">
<name>Apple</name>
</fruit>
<fruit color="orange">
<name>Orange</name>
</fruit>
<fruit color="green">
<name>Pear</name>
</fruit>
<fruit color="red">
<name>Watermelon</name>
</fruit>
</fruits>;
/* Displays:
<fruit color="red">
<name>Apple</name>
</fruit>
<fruit color="orange">
<name>Orange</name>
</fruit>
*/
trace( fruits.fruit.( /^[aeiouAEIOU].*/.test( name ) ) );
The preceding code snippet creates a regular expression (between the / and / ) that in plain English reads as "start with a vowel, upper- or lowercase, and be followed by any character any number of times." The test( ) method is invoked on the regular expression to test it against the parameter passed inin this case, the <name> element node, which is converted to its text node value for the particular <fruit> element being evaluated. Because the test( ) method returns a Boolean value, it's safe to use as part of predicate filter Boolean condition.
就是不能支持嵌套查询如:
xml..sprite.((anchor.@target == sp.anchor.@target) && (@id != sp.@id)).@id;