I did a lot of string parsing in the recent time: CSS Selectors, XML Display Objects, Stylesheets, … I also need XML selection from String expressions – I formerly (AS2) used the great XPath4AS2 from XFactorStudio which did it’s job well (though a bit slow, it’s AS2 after all).
There’s also one for Actionscript 3 (xpath-as3). But.. well… I wanted to go for some real speed! I like XPath a lot, but we now have native E4X selection in Actionscript 3, quite a different concept of node selection, and the conversion of XPath to E4X obviously results in quite a compromise in performance.
So all I need is a decent E4X parser. And hey, I found one! E4XParser from Digital Primates. It does its job really well, especially considering the very compact code it consists of. Thanks to some preparsing and caching, it’s also quite fast.
Still I thought I can do better :-) So I planted myself for a day (and a night) in front of my displays and hacked the hell out of it. The result is a little library which does pretty much the same thing as E4XParser, though pretty much more and a little faster too (15% to 50%). It’s about half as fast as the native E4X selection (once parsed). You can do nearly anything you can do with E4X. Use it like this:
import com.betabong.xml.e4x.E4X;
var result : XMLList = E4X.evaluate( xmllist , "author.( name.@last == 'Jobs' )" );
// E4X.evaluate( source : XMLList , expression : String ) : XMLList
If your source is XML, just do XMLList( xml ), if your result should be xml, do xml = result[0]
Test it here

Restrictions: You can’t use AND/OR in comparisions. So, this won’t go: author.( name.@first == ‘Steve’ && name.@last == ‘Jobs’ ) – though this is only a real limitations for OR. do this for AND: author.( name.@first == ‘Steve’ ).( name.@last == ‘Jobs’ ).
What you can do: Yes, you can do quite advanced stuff like author.( name.@first == name.@last ) or car.@rating.average() (one of the few proprietary functions I added). Or even
*..car.( @brand.toLowerCase() == 'volvo' ).( parent().( localName() == 'group' ).@rating > @rating )
– a weird example, I admit, but fancy, ain’t it? :-)
This is the first time ever I’m releasing part of my library as Open Source (MIT licence). As soon as I’ll find some time (and if I see any interest), I’m gonna put this into Google Code, so everybody can easily checkout and participate. Until then download it from here:
Download (zip 13kb)