lucene-java-user mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Dave Seltzer <dselt...@tveyes.com>
Subject Re: Creating Span Queries from Boolean Queries
Date Wed, 22 Aug 2012 02:06:07 GMT
So I've taken my first shot at solving my problem using the three functions
below.

When I set the slop to 10 it produces the following result:
This BooleanQuery +content:"london olympics" +(+content:football
+content:or +content:soccer) -content:nfl

becomes this SpanQuery: spanNot(spanNear([spanNear([content:london,
content:olympics], 0, true), spanNear([content:football, content:or,
content:soccer], 10, false)], 10, false), spanOr([content:nfl]))

Right now I've implemented TermQuery, PhraseQuery and BooleanQuery.

Is there a list of queries that could be produced using the Lucene Query
Parser? Any thoughts on how I should implement Wildcard queries?

Thanks!

-Dave


public static SpanQuery ConvertQuery(Query input, int slop) {
SpanQuery convertedQuery = null;
if(input instanceof TermQuery) {
//support for term query
convertedQuery = new SpanTermQuery(((TermQuery)input).getTerm());
} else if(input instanceof PhraseQuery) {
//support for phrase query
convertedQuery = ConvertPhraseQueryToSpanQuery((PhraseQuery)input);
} else if(input instanceof BooleanQuery) {
//support for nested boolean query
convertedQuery = ConvertBooleanQuery((BooleanQuery)input,slop);
}
return convertedQuery;
}


public static SpanQuery ConvertPhraseQueryToSpanQuery(PhraseQuery input) {
SpanQuery retval = null;
ArrayList<SpanQuery> terms = new ArrayList<SpanQuery>();
for(Term t : input.getTerms())
{
terms.add(new SpanTermQuery(t));
}
retval = new SpanNearQuery(terms.toArray(new SpanQuery[terms.size()]), 0,
true);
return retval;
}

public static SpanQuery ConvertBooleanQuery(BooleanQuery input, int slop) {
ArrayList<SpanQuery> andClauses = new ArrayList<SpanQuery>();
ArrayList<SpanQuery> orClauses = new ArrayList<SpanQuery>();
ArrayList<SpanQuery> notClauses = new ArrayList<SpanQuery>();
SpanQuery retval = null;

//iterate thorough any child clauses prior to
for(BooleanClause clause : ((BooleanQuery) input).clauses()) {
SpanQuery convertedQuery = ConvertQuery(clause.getQuery(), slop);
 if(convertedQuery != null)
{
if(clause.getOccur() == BooleanClause.Occur.MUST) {
andClauses.add(convertedQuery);
} else if (clause.getOccur() == BooleanClause.Occur.SHOULD) {
orClauses.add(convertedQuery);
} else if (clause.getOccur() == BooleanClause.Occur.MUST_NOT) {
notClauses.add(convertedQuery);
}
}
}
 //alright, now lets assemble the clauses that we've collected for this
query
SpanQuery andSpans = null;
SpanQuery  orSpans = null;
SpanQuery notSpans = null;
 //if there are no ANDs and no ORs then we'll return null
if(andClauses.size() + orClauses.size() == 0)
return null;
 if(andClauses.size() > 0) {
if(andClauses.size() > 1) {
andSpans = new SpanNearQuery(andClauses.toArray(new
SpanQuery[andClauses.size()]), slop, false);
} else {
andSpans = andClauses.get(0);
}
}
if(orClauses.size() > 0) {
orSpans = new SpanOrQuery(orClauses.toArray(new
SpanQuery[orClauses.size()]));
}
if(notClauses.size() > 0) {
notSpans = new SpanOrQuery(notClauses.toArray(new
SpanQuery[notClauses.size()]));
}
 //build an intermediate query using the above clauses
SpanQuery intermediateQuery = null;
if(andClauses.size() > 0 && orClauses.size() == 0) {
intermediateQuery = andSpans;
} else if (orClauses.size() > 0 && andClauses.size() == 0) {
intermediateQuery = orSpans;
} else {
intermediateQuery = new SpanNearQuery(new SpanQuery[]{andSpans,orSpans},
slop, false);
}
 //if we have any NOT queries append them to the end
if(notClauses.size() > 0) {
retval = new SpanNotQuery(intermediateQuery, notSpans);
} else {
retval = intermediateQuery;
}
 return retval;
}

Mime
  • Unnamed multipart/alternative (inline, None, 0 bytes)
View raw message