Good to hear from you too Jody! I actually was knee-deep in DefaultFilterVisitor when I wrote that email, and yet still managed to miss the fact that I could have written that visitor exactly as you wrote. I can only blame a lack of coffee. Thank you much for that pointer! --saul
________________________________ From: Jody Garnett [mailto:[EMAIL PROTECTED] Sent: Thu 8/2/2007 5:55 PM To: Farber, Saul (EEA) Cc: [email protected] Subject: Re: [Geotools-devel] DefaultFilterVisitor improvements Hi Saul - good to hear from you. For your specific case you will want to implement both a FilterVisitor and an ExpressionVisitor, by using the a default implementation that has all the methods stubbed you should be able to reduce your code example to a single method. The example you provided has been done a lot in the GeoTools code base by different developers; - http://docs.codehaus.org/display/GEOTDOC/FilterVisitor+Examples Here is the example from that page: > class FindNames extends DefaultFilterVisitor { > public Object visit( PropertyName expression, Object data ) { > Set set = (Set) data; > set.add( expression.getPropertyName() ); > > return set; > } > } > Set set = (Set) myFilter.accept( new FindNames(), new HashSet() ); Cheers, Jody Farber, Saul (EEA) wrote: > Hey all, > > I've been writing a little filtervisitor today, just to run through a filter > and collect some pertinent information. > > Problem is, that 'little' filtervisitor is actually enormous, because there's > not type-generalization built into DefaultFilterVisitor. > > Suppose I want to collect all the PropertyNames from a filter (so I can > figure out if someone has provided a filter but not asked for the > propertyname in their query). I write a little filtervisitor to check every > node of the filter and if it's a PropertyName expression, grab the property > name. > > My class gets really big really quick: > > Filter f = ... > FilterVisitor pnCollector = new DefaultFilterVisitor() { > public Object visit(And a, Object o) { > Iterator ichildren = a.getChildren().iterator(); > while (ichildren.hasNext()) { > ((Filter)ichildren.next()).accept(this, o); > } > return null; > } > > public Object visit (Or o, Object o) { > //duplicate method body of And, or else call to a shared function > } > > public Object visit (PropertyIsEqualTo p, Object o) { > p.getExpression1().accept(this, o); > p.getExpression2().accept(this, o); > } > > public Object visit(<every other BinaryComparisonOperator> p, Object o) { > //call to shared function that looks a lot like the above visit > PropIsEqualTo... > } > > public Object visit(<every BinarySpatialOperator> so, Object o) { > //call to shared function from EVERY binaryspatialoperator... > } > > ... etc ... > > }; > f.accept(pnCollector); > > > That's a long implementation that could be considerably shoretened by > including a few convenience methods in DefaultFilterVisitor. > > I propose the addition of methods like this: > > public Object visit (BinarySpatialOperator o, Object o) { > ... > } > > and > > public Object visit (BinaryComparisonOperator o, Object o) { > ... > } > > and > > public Object visit (Filter f, Object o) { > ... > } > > and so on (for all the various intermediate interfaces in between > org.opengis.filter.Filter and org.opengis.filter.<leaf-filter-types>, up-to > and including Filter itself) > > > > Further, I propose that DefaultFilterVisitor change its implementation of > 'public visit(<Leaf-filter-type> f, Object o)' to call the 'next up the > chain' interface. So, for example, the DefaultFilterVisitor impl of > 'visit(Touches f, Object o)' would look like: > > public Object visit(Touches t, Object o) { > return visit((BinarySpatialOperator)t, o); > } > > also, visit(bso) would look like: > public Object visit(BinarySpatialOperator f, Object o) { > return visit((SpatialOperator)f, o); > } > > etc. > > All the way up to Filter, for each type. > > > This would make those writing FilterVisitors have to write MUCH MUCH less > code, and would allow for good type-based dispatching by allowing someone to > interact with EXACTLY the bits of the filter that they're interested in with > much less code. > > > If this is a bit confusing for DefaultFilterVisitor, perhaps this could go > into a DefaultFilterVisitor subclass? Perhaps 'HierarchicalFilterVisitor' or > something? > > > I chatted with aaime about this, and his only concern was that those using > IDEs might be lead astray by having to only implement ONE filter callback > method (visit(Filter f, Object o)) and just use a big switch statement. I > agree this is a risk, but perhaps could be alleviated with good documentation. > > > Thoughts anyone? > > --saul > > > ------------------------------------------------------------------------- > This SF.net email is sponsored by: Splunk Inc. > Still grepping through log files to find problems? Stop. > Now Search log events and configuration files using AJAX and a browser. > Download your FREE copy of Splunk now >> http://get.splunk.com/ > _______________________________________________ > Geotools-devel mailing list > [email protected] > https://lists.sourceforge.net/lists/listinfo/geotools-devel > ------------------------------------------------------------------------- This SF.net email is sponsored by: Splunk Inc. Still grepping through log files to find problems? Stop. Now Search log events and configuration files using AJAX and a browser. Download your FREE copy of Splunk now >> http://get.splunk.com/ _______________________________________________ Geotools-devel mailing list [email protected] https://lists.sourceforge.net/lists/listinfo/geotools-devel
