Source Code Cross Referenced for QueryParser.java in  » Net » lucene-connector » org » apache » lucene » queryParser » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » Net » lucene connector » org.apache.lucene.queryParser 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


0001:        /* Generated By:JavaCC: Do not edit this line. QueryParser.java */
0002:        package org.apache.lucene.queryParser;
0003:
0004:        import java.util.Vector;
0005:        import java.io.*;
0006:        import java.text.*;
0007:        import java.util.*;
0008:        import org.apache.lucene.index.Term;
0009:        import org.apache.lucene.analysis.*;
0010:        import org.apache.lucene.document.*;
0011:        import org.apache.lucene.search.*;
0012:        import org.apache.lucene.util.Parameter;
0013:
0014:        /**
0015:         * This class is generated by JavaCC.  The most important method is
0016:         * {@link #parse(String)}.
0017:         *
0018:         * The syntax for query strings is as follows:
0019:         * A Query is a series of clauses.
0020:         * A clause may be prefixed by:
0021:         * <ul>
0022:         * <li> a plus (<code>+</code>) or a minus (<code>-</code>) sign, indicating
0023:         * that the clause is required or prohibited respectively; or
0024:         * <li> a term followed by a colon, indicating the field to be searched.
0025:         * This enables one to construct queries which search multiple fields.
0026:         * </ul>
0027:         *
0028:         * A clause may be either:
0029:         * <ul>
0030:         * <li> a term, indicating all the documents that contain this term; or
0031:         * <li> a nested query, enclosed in parentheses.  Note that this may be used
0032:         * with a <code>+</code>/<code>-</code> prefix to require any of a set of
0033:         * terms.
0034:         * </ul>
0035:         *
0036:         * Thus, in BNF, the query grammar is:
0037:         * <pre>
0038:         *   Query  ::= ( Clause )*
0039:         *   Clause ::= ["+", "-"] [&lt;TERM&gt; ":"] ( &lt;TERM&gt; | "(" Query ")" )
0040:         * </pre>
0041:         *
0042:         * <p>
0043:         * Examples of appropriately formatted queries can be found in the <a
0044:         * href="http://lucene.apache.org/java/docs/queryparsersyntax.html">query syntax
0045:         * documentation</a>.
0046:         * </p>
0047:         *
0048:         * <p>
0049:         * In {@link RangeQuery}s, QueryParser tries to detect date values, e.g.
0050:         * <tt>date:[6/1/2005 TO 6/4/2005]</tt> produces a range query that searches
0051:         * for "date" fields between 2005-06-01 and 2005-06-04. Note that the format
0052:         * of the accepted input depends on {@link #setLocale(Locale) the locale}.
0053:         * By default a date is converted into a search term using the deprecated
0054:         * {@link DateField} for compatibility reasons.
0055:         * To use the new {@link DateTools} to convert dates, a
0056:         * {@link org.apache.lucene.document.DateTools.Resolution} has to be set.
0057:         * </p>
0058:         * <p>
0059:         * The date resolution that shall be used for RangeQueries can be set
0060:         * using {@link #setDateResolution(DateTools.Resolution)}
0061:         * or {@link #setDateResolution(String, DateTools.Resolution)}. The former
0062:         * sets the default date resolution for all fields, whereas the latter can
0063:         * be used to set field specific date resolutions. Field specific date
0064:         * resolutions take, if set, precedence over the default date resolution.
0065:         * </p>
0066:         * <p>
0067:         * If you use neither {@link DateField} nor {@link DateTools} in your
0068:         * index, you can create your own
0069:         * query parser that inherits QueryParser and overwrites
0070:         * {@link #getRangeQuery(String, String, String, boolean)} to
0071:         * use a different method for date conversion.
0072:         * </p>
0073:         *
0074:         * <p>Note that QueryParser is <em>not</em> thread-safe.</p>
0075:         *
0076:         * @author Brian Goetz
0077:         * @author Peter Halacsy
0078:         * @author Tatu Saloranta
0079:         */
0080:        public class QueryParser implements  QueryParserConstants {
0081:
0082:            private static final int CONJ_NONE = 0;
0083:            private static final int CONJ_AND = 1;
0084:            private static final int CONJ_OR = 2;
0085:
0086:            private static final int MOD_NONE = 0;
0087:            private static final int MOD_NOT = 10;
0088:            private static final int MOD_REQ = 11;
0089:
0090:            // make it possible to call setDefaultOperator() without accessing 
0091:            // the nested class:
0092:            /** Alternative form of QueryParser.Operator.AND */
0093:            public static final Operator AND_OPERATOR = Operator.AND;
0094:            /** Alternative form of QueryParser.Operator.OR */
0095:            public static final Operator OR_OPERATOR = Operator.OR;
0096:
0097:            /** The actual operator that parser uses to combine query terms */
0098:            private Operator operator = OR_OPERATOR;
0099:
0100:            boolean lowercaseExpandedTerms = true;
0101:            boolean useOldRangeQuery = false;
0102:            boolean allowLeadingWildcard = false;
0103:            boolean enablePositionIncrements = false;
0104:
0105:            Analyzer analyzer;
0106:            String field;
0107:            int phraseSlop = 0;
0108:            float fuzzyMinSim = FuzzyQuery.defaultMinSimilarity;
0109:            int fuzzyPrefixLength = FuzzyQuery.defaultPrefixLength;
0110:            Locale locale = Locale.getDefault();
0111:
0112:            // the default date resolution
0113:            DateTools.Resolution dateResolution = null;
0114:            // maps field names to date resolutions
0115:            Map fieldToDateResolution = null;
0116:
0117:            /** The default operator for parsing queries. 
0118:             * Use {@link QueryParser#setDefaultOperator} to change it.
0119:             */
0120:            static public final class Operator extends Parameter {
0121:                private Operator(String name) {
0122:                    super (name);
0123:                }
0124:
0125:                static public final Operator OR = new Operator("OR");
0126:                static public final Operator AND = new Operator("AND");
0127:            }
0128:
0129:            /** Constructs a query parser.
0130:             *  @param f  the default field for query terms.
0131:             *  @param a   used to find terms in the query text.
0132:             */
0133:            public QueryParser(String f, Analyzer a) {
0134:                this (new FastCharStream(new StringReader("")));
0135:                analyzer = a;
0136:                field = f;
0137:            }
0138:
0139:            /** Parses a query string, returning a {@link org.apache.lucene.search.Query}.
0140:             *  @param query  the query string to be parsed.
0141:             *  @throws ParseException if the parsing fails
0142:             */
0143:            public Query parse(String query) throws ParseException {
0144:                ReInit(new FastCharStream(new StringReader(query)));
0145:                try {
0146:                    // TopLevelQuery is a Query followed by the end-of-input (EOF)
0147:                    Query res = TopLevelQuery(field);
0148:                    return res != null ? res : new BooleanQuery();
0149:                } catch (ParseException tme) {
0150:                    // rethrow to include the original query:
0151:                    throw new ParseException("Cannot parse '" + query + "': "
0152:                            + tme.getMessage());
0153:                } catch (TokenMgrError tme) {
0154:                    throw new ParseException("Cannot parse '" + query + "': "
0155:                            + tme.getMessage());
0156:                } catch (BooleanQuery.TooManyClauses tmc) {
0157:                    throw new ParseException("Cannot parse '" + query
0158:                            + "': too many boolean clauses");
0159:                }
0160:            }
0161:
0162:            /**
0163:             * @return Returns the analyzer.
0164:             */
0165:            public Analyzer getAnalyzer() {
0166:                return analyzer;
0167:            }
0168:
0169:            /**
0170:             * @return Returns the field.
0171:             */
0172:            public String getField() {
0173:                return field;
0174:            }
0175:
0176:            /**
0177:             * Get the minimal similarity for fuzzy queries.
0178:             */
0179:            public float getFuzzyMinSim() {
0180:                return fuzzyMinSim;
0181:            }
0182:
0183:            /**
0184:             * Set the minimum similarity for fuzzy queries.
0185:             * Default is 0.5f.
0186:             */
0187:            public void setFuzzyMinSim(float fuzzyMinSim) {
0188:                this .fuzzyMinSim = fuzzyMinSim;
0189:            }
0190:
0191:            /**
0192:             * Get the prefix length for fuzzy queries. 
0193:             * @return Returns the fuzzyPrefixLength.
0194:             */
0195:            public int getFuzzyPrefixLength() {
0196:                return fuzzyPrefixLength;
0197:            }
0198:
0199:            /**
0200:             * Set the prefix length for fuzzy queries. Default is 0.
0201:             * @param fuzzyPrefixLength The fuzzyPrefixLength to set.
0202:             */
0203:            public void setFuzzyPrefixLength(int fuzzyPrefixLength) {
0204:                this .fuzzyPrefixLength = fuzzyPrefixLength;
0205:            }
0206:
0207:            /**
0208:             * Sets the default slop for phrases.  If zero, then exact phrase matches
0209:             * are required.  Default value is zero.
0210:             */
0211:            public void setPhraseSlop(int phraseSlop) {
0212:                this .phraseSlop = phraseSlop;
0213:            }
0214:
0215:            /**
0216:             * Gets the default slop for phrases.
0217:             */
0218:            public int getPhraseSlop() {
0219:                return phraseSlop;
0220:            }
0221:
0222:            /**
0223:             * Set to <code>true</code> to allow leading wildcard characters.
0224:             * <p>
0225:             * When set, <code>*</code> or <code>?</code> are allowed as 
0226:             * the first character of a PrefixQuery and WildcardQuery.
0227:             * Note that this can produce very slow
0228:             * queries on big indexes. 
0229:             * <p>
0230:             * Default: false.
0231:             */
0232:            public void setAllowLeadingWildcard(boolean allowLeadingWildcard) {
0233:                this .allowLeadingWildcard = allowLeadingWildcard;
0234:            }
0235:
0236:            /**
0237:             * @see #setAllowLeadingWildcard(boolean)
0238:             */
0239:            public boolean getAllowLeadingWildcard() {
0240:                return allowLeadingWildcard;
0241:            }
0242:
0243:            /**
0244:             * Set to <code>true</code> to enable position increments in result query.
0245:             * <p>
0246:             * When set, result phrase and multi-phrase queries will
0247:             * be aware of position increments.
0248:             * Useful when e.g. a StopFilter increases the position increment of
0249:             * the token that follows an omitted token.
0250:             * <p>
0251:             * Default: false.
0252:             */
0253:            public void setEnablePositionIncrements(boolean enable) {
0254:                this .enablePositionIncrements = enable;
0255:            }
0256:
0257:            /**
0258:             * @see #setEnablePositionIncrements(boolean)
0259:             */
0260:            public boolean getEnablePositionIncrements() {
0261:                return enablePositionIncrements;
0262:            }
0263:
0264:            /**
0265:             * Sets the boolean operator of the QueryParser.
0266:             * In default mode (<code>OR_OPERATOR</code>) terms without any modifiers
0267:             * are considered optional: for example <code>capital of Hungary</code> is equal to
0268:             * <code>capital OR of OR Hungary</code>.<br/>
0269:             * In <code>AND_OPERATOR</code> mode terms are considered to be in conjuction: the
0270:             * above mentioned query is parsed as <code>capital AND of AND Hungary</code>
0271:             */
0272:            public void setDefaultOperator(Operator op) {
0273:                this .operator = op;
0274:            }
0275:
0276:            /**
0277:             * Gets implicit operator setting, which will be either AND_OPERATOR
0278:             * or OR_OPERATOR.
0279:             */
0280:            public Operator getDefaultOperator() {
0281:                return operator;
0282:            }
0283:
0284:            /**
0285:             * Whether terms of wildcard, prefix, fuzzy and range queries are to be automatically
0286:             * lower-cased or not.  Default is <code>true</code>.
0287:             */
0288:            public void setLowercaseExpandedTerms(boolean lowercaseExpandedTerms) {
0289:                this .lowercaseExpandedTerms = lowercaseExpandedTerms;
0290:            }
0291:
0292:            /**
0293:             * @see #setLowercaseExpandedTerms(boolean)
0294:             */
0295:            public boolean getLowercaseExpandedTerms() {
0296:                return lowercaseExpandedTerms;
0297:            }
0298:
0299:            /**
0300:             * By default QueryParser uses new ConstantScoreRangeQuery in preference to RangeQuery
0301:             * for range queries. This implementation is generally preferable because it 
0302:             * a) Runs faster b) Does not have the scarcity of range terms unduly influence score 
0303:             * c) avoids any "TooManyBooleanClauses" exception.
0304:             * However, if your application really needs to use the old-fashioned RangeQuery and the above
0305:             * points are not required then set this option to <code>true</code>
0306:             * Default is <code>false</code>.
0307:             */
0308:            public void setUseOldRangeQuery(boolean useOldRangeQuery) {
0309:                this .useOldRangeQuery = useOldRangeQuery;
0310:            }
0311:
0312:            /**
0313:             * @see #setUseOldRangeQuery(boolean)
0314:             */
0315:            public boolean getUseOldRangeQuery() {
0316:                return useOldRangeQuery;
0317:            }
0318:
0319:            /**
0320:             * Set locale used by date range parsing.
0321:             */
0322:            public void setLocale(Locale locale) {
0323:                this .locale = locale;
0324:            }
0325:
0326:            /**
0327:             * Returns current locale, allowing access by subclasses.
0328:             */
0329:            public Locale getLocale() {
0330:                return locale;
0331:            }
0332:
0333:            /**
0334:             * Sets the default date resolution used by RangeQueries for fields for which no
0335:             * specific date resolutions has been set. Field specific resolutions can be set
0336:             * with {@link #setDateResolution(String, DateTools.Resolution)}.
0337:             *  
0338:             * @param dateResolution the default date resolution to set
0339:             */
0340:            public void setDateResolution(DateTools.Resolution dateResolution) {
0341:                this .dateResolution = dateResolution;
0342:            }
0343:
0344:            /**
0345:             * Sets the date resolution used by RangeQueries for a specific field.
0346:             *  
0347:             * @param fieldName field for which the date resolution is to be set 
0348:             * @param dateResolution date resolution to set
0349:             */
0350:            public void setDateResolution(String fieldName,
0351:                    DateTools.Resolution dateResolution) {
0352:                if (fieldName == null) {
0353:                    throw new IllegalArgumentException("Field cannot be null.");
0354:                }
0355:
0356:                if (fieldToDateResolution == null) {
0357:                    // lazily initialize HashMap
0358:                    fieldToDateResolution = new HashMap();
0359:                }
0360:
0361:                fieldToDateResolution.put(fieldName, dateResolution);
0362:            }
0363:
0364:            /**
0365:             * Returns the date resolution that is used by RangeQueries for the given field. 
0366:             * Returns null, if no default or field specific date resolution has been set
0367:             * for the given field.
0368:             *
0369:             */
0370:            public DateTools.Resolution getDateResolution(String fieldName) {
0371:                if (fieldName == null) {
0372:                    throw new IllegalArgumentException("Field cannot be null.");
0373:                }
0374:
0375:                if (fieldToDateResolution == null) {
0376:                    // no field specific date resolutions set; return default date resolution instead
0377:                    return this .dateResolution;
0378:                }
0379:
0380:                DateTools.Resolution resolution = (DateTools.Resolution) fieldToDateResolution
0381:                        .get(fieldName);
0382:                if (resolution == null) {
0383:                    // no date resolutions set for the given field; return default date resolution instead
0384:                    resolution = this .dateResolution;
0385:                }
0386:
0387:                return resolution;
0388:            }
0389:
0390:            protected void addClause(Vector clauses, int conj, int mods, Query q) {
0391:                boolean required, prohibited;
0392:
0393:                // If this term is introduced by AND, make the preceding term required,
0394:                // unless it's already prohibited
0395:                if (clauses.size() > 0 && conj == CONJ_AND) {
0396:                    BooleanClause c = (BooleanClause) clauses.elementAt(clauses
0397:                            .size() - 1);
0398:                    if (!c.isProhibited())
0399:                        c.setOccur(BooleanClause.Occur.MUST);
0400:                }
0401:
0402:                if (clauses.size() > 0 && operator == AND_OPERATOR
0403:                        && conj == CONJ_OR) {
0404:                    // If this term is introduced by OR, make the preceding term optional,
0405:                    // unless it's prohibited (that means we leave -a OR b but +a OR b-->a OR b)
0406:                    // notice if the input is a OR b, first term is parsed as required; without
0407:                    // this modification a OR b would parsed as +a OR b
0408:                    BooleanClause c = (BooleanClause) clauses.elementAt(clauses
0409:                            .size() - 1);
0410:                    if (!c.isProhibited())
0411:                        c.setOccur(BooleanClause.Occur.SHOULD);
0412:                }
0413:
0414:                // We might have been passed a null query; the term might have been
0415:                // filtered away by the analyzer.
0416:                if (q == null)
0417:                    return;
0418:
0419:                if (operator == OR_OPERATOR) {
0420:                    // We set REQUIRED if we're introduced by AND or +; PROHIBITED if
0421:                    // introduced by NOT or -; make sure not to set both.
0422:                    prohibited = (mods == MOD_NOT);
0423:                    required = (mods == MOD_REQ);
0424:                    if (conj == CONJ_AND && !prohibited) {
0425:                        required = true;
0426:                    }
0427:                } else {
0428:                    // We set PROHIBITED if we're introduced by NOT or -; We set REQUIRED
0429:                    // if not PROHIBITED and not introduced by OR
0430:                    prohibited = (mods == MOD_NOT);
0431:                    required = (!prohibited && conj != CONJ_OR);
0432:                }
0433:                if (required && !prohibited)
0434:                    clauses.addElement(new BooleanClause(q,
0435:                            BooleanClause.Occur.MUST));
0436:                else if (!required && !prohibited)
0437:                    clauses.addElement(new BooleanClause(q,
0438:                            BooleanClause.Occur.SHOULD));
0439:                else if (!required && prohibited)
0440:                    clauses.addElement(new BooleanClause(q,
0441:                            BooleanClause.Occur.MUST_NOT));
0442:                else
0443:                    throw new RuntimeException(
0444:                            "Clause cannot be both required and prohibited");
0445:            }
0446:
0447:            /**
0448:             * @exception ParseException throw in overridden method to disallow
0449:             */
0450:            protected Query getFieldQuery(String field, String queryText)
0451:                    throws ParseException {
0452:                // Use the analyzer to get all the tokens, and then build a TermQuery,
0453:                // PhraseQuery, or nothing based on the term count
0454:
0455:                TokenStream source = analyzer.tokenStream(field,
0456:                        new StringReader(queryText));
0457:                Vector v = new Vector();
0458:                org.apache.lucene.analysis.Token t;
0459:                int positionCount = 0;
0460:                boolean severalTokensAtSamePosition = false;
0461:
0462:                while (true) {
0463:                    try {
0464:                        t = source.next();
0465:                    } catch (IOException e) {
0466:                        t = null;
0467:                    }
0468:                    if (t == null)
0469:                        break;
0470:                    v.addElement(t);
0471:                    if (t.getPositionIncrement() != 0)
0472:                        positionCount += t.getPositionIncrement();
0473:                    else
0474:                        severalTokensAtSamePosition = true;
0475:                }
0476:                try {
0477:                    source.close();
0478:                } catch (IOException e) {
0479:                    // ignore
0480:                }
0481:
0482:                if (v.size() == 0)
0483:                    return null;
0484:                else if (v.size() == 1) {
0485:                    t = (org.apache.lucene.analysis.Token) v.elementAt(0);
0486:                    return new TermQuery(new Term(field, t.termText()));
0487:                } else {
0488:                    if (severalTokensAtSamePosition) {
0489:                        if (positionCount == 1) {
0490:                            // no phrase query:
0491:                            BooleanQuery q = new BooleanQuery(true);
0492:                            for (int i = 0; i < v.size(); i++) {
0493:                                t = (org.apache.lucene.analysis.Token) v
0494:                                        .elementAt(i);
0495:                                TermQuery currentQuery = new TermQuery(
0496:                                        new Term(field, t.termText()));
0497:                                q.add(currentQuery, BooleanClause.Occur.SHOULD);
0498:                            }
0499:                            return q;
0500:                        } else {
0501:                            // phrase query:
0502:                            MultiPhraseQuery mpq = new MultiPhraseQuery();
0503:                            mpq.setSlop(phraseSlop);
0504:                            List multiTerms = new ArrayList();
0505:                            int position = -1;
0506:                            for (int i = 0; i < v.size(); i++) {
0507:                                t = (org.apache.lucene.analysis.Token) v
0508:                                        .elementAt(i);
0509:                                if (t.getPositionIncrement() > 0
0510:                                        && multiTerms.size() > 0) {
0511:                                    if (enablePositionIncrements) {
0512:                                        mpq
0513:                                                .add((Term[]) multiTerms
0514:                                                        .toArray(new Term[0]),
0515:                                                        position);
0516:                                    } else {
0517:                                        mpq.add((Term[]) multiTerms
0518:                                                .toArray(new Term[0]));
0519:                                    }
0520:                                    multiTerms.clear();
0521:                                }
0522:                                position += t.getPositionIncrement();
0523:                                multiTerms.add(new Term(field, t.termText()));
0524:                            }
0525:                            if (enablePositionIncrements) {
0526:                                mpq.add((Term[]) multiTerms
0527:                                        .toArray(new Term[0]), position);
0528:                            } else {
0529:                                mpq.add((Term[]) multiTerms
0530:                                        .toArray(new Term[0]));
0531:                            }
0532:                            return mpq;
0533:                        }
0534:                    } else {
0535:                        PhraseQuery pq = new PhraseQuery();
0536:                        pq.setSlop(phraseSlop);
0537:                        int position = -1;
0538:                        for (int i = 0; i < v.size(); i++) {
0539:                            t = (org.apache.lucene.analysis.Token) v
0540:                                    .elementAt(i);
0541:                            if (enablePositionIncrements) {
0542:                                position += t.getPositionIncrement();
0543:                                pq.add(new Term(field, t.termText()), position);
0544:                            } else {
0545:                                pq.add(new Term(field, t.termText()));
0546:                            }
0547:                        }
0548:                        return pq;
0549:                    }
0550:                }
0551:            }
0552:
0553:            /**
0554:             * Base implementation delegates to {@link #getFieldQuery(String,String)}.
0555:             * This method may be overridden, for example, to return
0556:             * a SpanNearQuery instead of a PhraseQuery.
0557:             *
0558:             * @exception ParseException throw in overridden method to disallow
0559:             */
0560:            protected Query getFieldQuery(String field, String queryText,
0561:                    int slop) throws ParseException {
0562:                Query query = getFieldQuery(field, queryText);
0563:
0564:                if (query instanceof  PhraseQuery) {
0565:                    ((PhraseQuery) query).setSlop(slop);
0566:                }
0567:                if (query instanceof  MultiPhraseQuery) {
0568:                    ((MultiPhraseQuery) query).setSlop(slop);
0569:                }
0570:
0571:                return query;
0572:            }
0573:
0574:            /**
0575:             * @exception ParseException throw in overridden method to disallow
0576:             */
0577:            protected Query getRangeQuery(String field, String part1,
0578:                    String part2, boolean inclusive) throws ParseException {
0579:                if (lowercaseExpandedTerms) {
0580:                    part1 = part1.toLowerCase();
0581:                    part2 = part2.toLowerCase();
0582:                }
0583:                try {
0584:                    DateFormat df = DateFormat.getDateInstance(
0585:                            DateFormat.SHORT, locale);
0586:                    df.setLenient(true);
0587:                    Date d1 = df.parse(part1);
0588:                    Date d2 = df.parse(part2);
0589:                    if (inclusive) {
0590:                        // The user can only specify the date, not the time, so make sure
0591:                        // the time is set to the latest possible time of that date to really
0592:                        // include all documents:
0593:                        Calendar cal = Calendar.getInstance(locale);
0594:                        cal.setTime(d2);
0595:                        cal.set(Calendar.HOUR_OF_DAY, 23);
0596:                        cal.set(Calendar.MINUTE, 59);
0597:                        cal.set(Calendar.SECOND, 59);
0598:                        cal.set(Calendar.MILLISECOND, 999);
0599:                        d2 = cal.getTime();
0600:                    }
0601:                    DateTools.Resolution resolution = getDateResolution(field);
0602:                    if (resolution == null) {
0603:                        // no default or field specific date resolution has been set,
0604:                        // use deprecated DateField to maintain compatibilty with
0605:                        // pre-1.9 Lucene versions.
0606:                        part1 = DateField.dateToString(d1);
0607:                        part2 = DateField.dateToString(d2);
0608:                    } else {
0609:                        part1 = DateTools.dateToString(d1, resolution);
0610:                        part2 = DateTools.dateToString(d2, resolution);
0611:                    }
0612:                } catch (Exception e) {
0613:                }
0614:
0615:                if (useOldRangeQuery) {
0616:                    return new RangeQuery(new Term(field, part1), new Term(
0617:                            field, part2), inclusive);
0618:                } else {
0619:                    return new ConstantScoreRangeQuery(field, part1, part2,
0620:                            inclusive, inclusive);
0621:                }
0622:            }
0623:
0624:            /**
0625:             * Factory method for generating query, given a set of clauses.
0626:             * By default creates a boolean query composed of clauses passed in.
0627:             *
0628:             * Can be overridden by extending classes, to modify query being
0629:             * returned.
0630:             *
0631:             * @param clauses Vector that contains {@link BooleanClause} instances
0632:             *    to join.
0633:             *
0634:             * @return Resulting {@link Query} object.
0635:             * @exception ParseException throw in overridden method to disallow
0636:             */
0637:            protected Query getBooleanQuery(Vector clauses)
0638:                    throws ParseException {
0639:                return getBooleanQuery(clauses, false);
0640:            }
0641:
0642:            /**
0643:             * Factory method for generating query, given a set of clauses.
0644:             * By default creates a boolean query composed of clauses passed in.
0645:             *
0646:             * Can be overridden by extending classes, to modify query being
0647:             * returned.
0648:             *
0649:             * @param clauses Vector that contains {@link BooleanClause} instances
0650:             *    to join.
0651:             * @param disableCoord true if coord scoring should be disabled.
0652:             *
0653:             * @return Resulting {@link Query} object.
0654:             * @exception ParseException throw in overridden method to disallow
0655:             */
0656:            protected Query getBooleanQuery(Vector clauses, boolean disableCoord)
0657:                    throws ParseException {
0658:                if (clauses.size() == 0) {
0659:                    return null; // all clause words were filtered away by the analyzer.
0660:                }
0661:                BooleanQuery query = new BooleanQuery(disableCoord);
0662:                for (int i = 0; i < clauses.size(); i++) {
0663:                    query.add((BooleanClause) clauses.elementAt(i));
0664:                }
0665:                return query;
0666:            }
0667:
0668:            /**
0669:             * Factory method for generating a query. Called when parser
0670:             * parses an input term token that contains one or more wildcard
0671:             * characters (? and *), but is not a prefix term token (one
0672:             * that has just a single * character at the end)
0673:             *<p>
0674:             * Depending on settings, prefix term may be lower-cased
0675:             * automatically. It will not go through the default Analyzer,
0676:             * however, since normal Analyzers are unlikely to work properly
0677:             * with wildcard templates.
0678:             *<p>
0679:             * Can be overridden by extending classes, to provide custom handling for
0680:             * wildcard queries, which may be necessary due to missing analyzer calls.
0681:             *
0682:             * @param field Name of the field query will use.
0683:             * @param termStr Term token that contains one or more wild card
0684:             *   characters (? or *), but is not simple prefix term
0685:             *
0686:             * @return Resulting {@link Query} built for the term
0687:             * @exception ParseException throw in overridden method to disallow
0688:             */
0689:            protected Query getWildcardQuery(String field, String termStr)
0690:                    throws ParseException {
0691:                if ("*".equals(field)) {
0692:                    if ("*".equals(termStr))
0693:                        return new MatchAllDocsQuery();
0694:                }
0695:                if (!allowLeadingWildcard
0696:                        && (termStr.startsWith("*") || termStr.startsWith("?")))
0697:                    throw new ParseException(
0698:                            "'*' or '?' not allowed as first character in WildcardQuery");
0699:                if (lowercaseExpandedTerms) {
0700:                    termStr = termStr.toLowerCase();
0701:                }
0702:                Term t = new Term(field, termStr);
0703:                return new WildcardQuery(t);
0704:            }
0705:
0706:            /**
0707:             * Factory method for generating a query (similar to
0708:             * {@link #getWildcardQuery}). Called when parser parses an input term
0709:             * token that uses prefix notation; that is, contains a single '*' wildcard
0710:             * character as its last character. Since this is a special case
0711:             * of generic wildcard term, and such a query can be optimized easily,
0712:             * this usually results in a different query object.
0713:             *<p>
0714:             * Depending on settings, a prefix term may be lower-cased
0715:             * automatically. It will not go through the default Analyzer,
0716:             * however, since normal Analyzers are unlikely to work properly
0717:             * with wildcard templates.
0718:             *<p>
0719:             * Can be overridden by extending classes, to provide custom handling for
0720:             * wild card queries, which may be necessary due to missing analyzer calls.
0721:             *
0722:             * @param field Name of the field query will use.
0723:             * @param termStr Term token to use for building term for the query
0724:             *    (<b>without</b> trailing '*' character!)
0725:             *
0726:             * @return Resulting {@link Query} built for the term
0727:             * @exception ParseException throw in overridden method to disallow
0728:             */
0729:            protected Query getPrefixQuery(String field, String termStr)
0730:                    throws ParseException {
0731:                if (!allowLeadingWildcard && termStr.startsWith("*"))
0732:                    throw new ParseException(
0733:                            "'*' not allowed as first character in PrefixQuery");
0734:                if (lowercaseExpandedTerms) {
0735:                    termStr = termStr.toLowerCase();
0736:                }
0737:                Term t = new Term(field, termStr);
0738:                return new PrefixQuery(t);
0739:            }
0740:
0741:            /**
0742:             * Factory method for generating a query (similar to
0743:             * {@link #getWildcardQuery}). Called when parser parses
0744:             * an input term token that has the fuzzy suffix (~) appended.
0745:             *
0746:             * @param field Name of the field query will use.
0747:             * @param termStr Term token to use for building term for the query
0748:             *
0749:             * @return Resulting {@link Query} built for the term
0750:             * @exception ParseException throw in overridden method to disallow
0751:             */
0752:            protected Query getFuzzyQuery(String field, String termStr,
0753:                    float minSimilarity) throws ParseException {
0754:                if (lowercaseExpandedTerms) {
0755:                    termStr = termStr.toLowerCase();
0756:                }
0757:                Term t = new Term(field, termStr);
0758:                return new FuzzyQuery(t, minSimilarity, fuzzyPrefixLength);
0759:            }
0760:
0761:            /**
0762:             * Returns a String where the escape char has been
0763:             * removed, or kept only once if there was a double escape.
0764:             * 
0765:             * Supports escaped unicode characters, e. g. translates
0766:             * <code>A</code> to <code>A</code>.
0767:             * 
0768:             */
0769:            private String discardEscapeChar(String input)
0770:                    throws ParseException {
0771:                // Create char array to hold unescaped char sequence
0772:                char[] output = new char[input.length()];
0773:
0774:                // The length of the output can be less than the input
0775:                // due to discarded escape chars. This variable holds
0776:                // the actual length of the output
0777:                int length = 0;
0778:
0779:                // We remember whether the last processed character was 
0780:                // an escape character
0781:                boolean lastCharWasEscapeChar = false;
0782:
0783:                // The multiplier the current unicode digit must be multiplied with.
0784:                // E. g. the first digit must be multiplied with 16^3, the second with 16^2...
0785:                int codePointMultiplier = 0;
0786:
0787:                // Used to calculate the codepoint of the escaped unicode character
0788:                int codePoint = 0;
0789:
0790:                for (int i = 0; i < input.length(); i++) {
0791:                    char curChar = input.charAt(i);
0792:                    if (codePointMultiplier > 0) {
0793:                        codePoint += hexToInt(curChar) * codePointMultiplier;
0794:                        codePointMultiplier >>>= 4;
0795:                        if (codePointMultiplier == 0) {
0796:                            output[length++] = (char) codePoint;
0797:                            codePoint = 0;
0798:                        }
0799:                    } else if (lastCharWasEscapeChar) {
0800:                        if (curChar == 'u') {
0801:                            // found an escaped unicode character
0802:                            codePointMultiplier = 16 * 16 * 16;
0803:                        } else {
0804:                            // this character was escaped
0805:                            output[length] = curChar;
0806:                            length++;
0807:                        }
0808:                        lastCharWasEscapeChar = false;
0809:                    } else {
0810:                        if (curChar == '\\') {
0811:                            lastCharWasEscapeChar = true;
0812:                        } else {
0813:                            output[length] = curChar;
0814:                            length++;
0815:                        }
0816:                    }
0817:                }
0818:
0819:                if (codePointMultiplier > 0) {
0820:                    throw new ParseException(
0821:                            "Truncated unicode escape sequence.");
0822:                }
0823:
0824:                if (lastCharWasEscapeChar) {
0825:                    throw new ParseException(
0826:                            "Term can not end with escape character.");
0827:                }
0828:
0829:                return new String(output, 0, length);
0830:            }
0831:
0832:            /** Returns the numeric value of the hexadecimal character */
0833:            private static final int hexToInt(char c) throws ParseException {
0834:                if ('0' <= c && c <= '9') {
0835:                    return c - '0';
0836:                } else if ('a' <= c && c <= 'f') {
0837:                    return c - 'a' + 10;
0838:                } else if ('A' <= c && c <= 'F') {
0839:                    return c - 'A' + 10;
0840:                } else {
0841:                    throw new ParseException(
0842:                            "None-hex character in unicode escape sequence: "
0843:                                    + c);
0844:                }
0845:            }
0846:
0847:            /**
0848:             * Returns a String where those characters that QueryParser
0849:             * expects to be escaped are escaped by a preceding <code>\</code>.
0850:             */
0851:            public static String escape(String s) {
0852:                StringBuffer sb = new StringBuffer();
0853:                for (int i = 0; i < s.length(); i++) {
0854:                    char c = s.charAt(i);
0855:                    // These characters are part of the query syntax and must be escaped
0856:                    if (c == '\\' || c == '+' || c == '-' || c == '!'
0857:                            || c == '(' || c == ')' || c == ':' || c == '^'
0858:                            || c == '[' || c == ']' || c == '\"' || c == '{'
0859:                            || c == '}' || c == '~' || c == '*' || c == '?'
0860:                            || c == '|' || c == '&') {
0861:                        sb.append('\\');
0862:                    }
0863:                    sb.append(c);
0864:                }
0865:                return sb.toString();
0866:            }
0867:
0868:            /**
0869:             * Command line tool to test QueryParser, using {@link org.apache.lucene.analysis.SimpleAnalyzer}.
0870:             * Usage:<br>
0871:             * <code>java org.apache.lucene.queryParser.QueryParser &lt;input&gt;</code>
0872:             */
0873:            public static void main(String[] args) throws Exception {
0874:                if (args.length == 0) {
0875:                    System.out
0876:                            .println("Usage: java org.apache.lucene.queryParser.QueryParser <input>");
0877:                    System.exit(0);
0878:                }
0879:                QueryParser qp = new QueryParser("field",
0880:                        new org.apache.lucene.analysis.SimpleAnalyzer());
0881:                Query q = qp.parse(args[0]);
0882:                System.out.println(q.toString("field"));
0883:            }
0884:
0885:            // *   Query  ::= ( Clause )*
0886:            // *   Clause ::= ["+", "-"] [<TERM> ":"] ( <TERM> | "(" Query ")" )
0887:            final public int Conjunction() throws ParseException {
0888:                int ret = CONJ_NONE;
0889:                switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
0890:                case AND:
0891:                case OR:
0892:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
0893:                    case AND:
0894:                        jj_consume_token(AND);
0895:                        ret = CONJ_AND;
0896:                        break;
0897:                    case OR:
0898:                        jj_consume_token(OR);
0899:                        ret = CONJ_OR;
0900:                        break;
0901:                    default:
0902:                        jj_la1[0] = jj_gen;
0903:                        jj_consume_token(-1);
0904:                        throw new ParseException();
0905:                    }
0906:                    break;
0907:                default:
0908:                    jj_la1[1] = jj_gen;
0909:                    ;
0910:                }
0911:                {
0912:                    if (true)
0913:                        return ret;
0914:                }
0915:                throw new Error("Missing return statement in function");
0916:            }
0917:
0918:            final public int Modifiers() throws ParseException {
0919:                int ret = MOD_NONE;
0920:                switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
0921:                case NOT:
0922:                case PLUS:
0923:                case MINUS:
0924:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
0925:                    case PLUS:
0926:                        jj_consume_token(PLUS);
0927:                        ret = MOD_REQ;
0928:                        break;
0929:                    case MINUS:
0930:                        jj_consume_token(MINUS);
0931:                        ret = MOD_NOT;
0932:                        break;
0933:                    case NOT:
0934:                        jj_consume_token(NOT);
0935:                        ret = MOD_NOT;
0936:                        break;
0937:                    default:
0938:                        jj_la1[2] = jj_gen;
0939:                        jj_consume_token(-1);
0940:                        throw new ParseException();
0941:                    }
0942:                    break;
0943:                default:
0944:                    jj_la1[3] = jj_gen;
0945:                    ;
0946:                }
0947:                {
0948:                    if (true)
0949:                        return ret;
0950:                }
0951:                throw new Error("Missing return statement in function");
0952:            }
0953:
0954:            // This makes sure that there is no garbage after the query string
0955:            final public Query TopLevelQuery(String field)
0956:                    throws ParseException {
0957:                Query q;
0958:                q = Query(field);
0959:                jj_consume_token(0);
0960:                {
0961:                    if (true)
0962:                        return q;
0963:                }
0964:                throw new Error("Missing return statement in function");
0965:            }
0966:
0967:            final public Query Query(String field) throws ParseException {
0968:                Vector clauses = new Vector();
0969:                Query q, firstQuery = null;
0970:                int conj, mods;
0971:                mods = Modifiers();
0972:                q = Clause(field);
0973:                addClause(clauses, CONJ_NONE, mods, q);
0974:                if (mods == MOD_NONE)
0975:                    firstQuery = q;
0976:                label_1: while (true) {
0977:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
0978:                    case AND:
0979:                    case OR:
0980:                    case NOT:
0981:                    case PLUS:
0982:                    case MINUS:
0983:                    case LPAREN:
0984:                    case STAR:
0985:                    case QUOTED:
0986:                    case TERM:
0987:                    case PREFIXTERM:
0988:                    case WILDTERM:
0989:                    case RANGEIN_START:
0990:                    case RANGEEX_START:
0991:                    case NUMBER:
0992:                        ;
0993:                        break;
0994:                    default:
0995:                        jj_la1[4] = jj_gen;
0996:                        break label_1;
0997:                    }
0998:                    conj = Conjunction();
0999:                    mods = Modifiers();
1000:                    q = Clause(field);
1001:                    addClause(clauses, conj, mods, q);
1002:                }
1003:                if (clauses.size() == 1 && firstQuery != null) {
1004:                    if (true)
1005:                        return firstQuery;
1006:                } else {
1007:                    {
1008:                        if (true)
1009:                            return getBooleanQuery(clauses);
1010:                    }
1011:                }
1012:                throw new Error("Missing return statement in function");
1013:            }
1014:
1015:            final public Query Clause(String field) throws ParseException {
1016:                Query q;
1017:                Token fieldToken = null, boost = null;
1018:                if (jj_2_1(2)) {
1019:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1020:                    case TERM:
1021:                        fieldToken = jj_consume_token(TERM);
1022:                        jj_consume_token(COLON);
1023:                        field = discardEscapeChar(fieldToken.image);
1024:                        break;
1025:                    case STAR:
1026:                        jj_consume_token(STAR);
1027:                        jj_consume_token(COLON);
1028:                        field = "*";
1029:                        break;
1030:                    default:
1031:                        jj_la1[5] = jj_gen;
1032:                        jj_consume_token(-1);
1033:                        throw new ParseException();
1034:                    }
1035:                } else {
1036:                    ;
1037:                }
1038:                switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1039:                case STAR:
1040:                case QUOTED:
1041:                case TERM:
1042:                case PREFIXTERM:
1043:                case WILDTERM:
1044:                case RANGEIN_START:
1045:                case RANGEEX_START:
1046:                case NUMBER:
1047:                    q = Term(field);
1048:                    break;
1049:                case LPAREN:
1050:                    jj_consume_token(LPAREN);
1051:                    q = Query(field);
1052:                    jj_consume_token(RPAREN);
1053:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1054:                    case CARAT:
1055:                        jj_consume_token(CARAT);
1056:                        boost = jj_consume_token(NUMBER);
1057:                        break;
1058:                    default:
1059:                        jj_la1[6] = jj_gen;
1060:                        ;
1061:                    }
1062:                    break;
1063:                default:
1064:                    jj_la1[7] = jj_gen;
1065:                    jj_consume_token(-1);
1066:                    throw new ParseException();
1067:                }
1068:                if (boost != null) {
1069:                    float f = (float) 1.0;
1070:                    try {
1071:                        f = Float.valueOf(boost.image).floatValue();
1072:                        q.setBoost(f);
1073:                    } catch (Exception ignored) {
1074:                    }
1075:                }
1076:                {
1077:                    if (true)
1078:                        return q;
1079:                }
1080:                throw new Error("Missing return statement in function");
1081:            }
1082:
1083:            final public Query Term(String field) throws ParseException {
1084:                Token term, boost = null, fuzzySlop = null, goop1, goop2;
1085:                boolean prefix = false;
1086:                boolean wildcard = false;
1087:                boolean fuzzy = false;
1088:                boolean rangein = false;
1089:                Query q;
1090:                switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1091:                case STAR:
1092:                case TERM:
1093:                case PREFIXTERM:
1094:                case WILDTERM:
1095:                case NUMBER:
1096:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1097:                    case TERM:
1098:                        term = jj_consume_token(TERM);
1099:                        break;
1100:                    case STAR:
1101:                        term = jj_consume_token(STAR);
1102:                        wildcard = true;
1103:                        break;
1104:                    case PREFIXTERM:
1105:                        term = jj_consume_token(PREFIXTERM);
1106:                        prefix = true;
1107:                        break;
1108:                    case WILDTERM:
1109:                        term = jj_consume_token(WILDTERM);
1110:                        wildcard = true;
1111:                        break;
1112:                    case NUMBER:
1113:                        term = jj_consume_token(NUMBER);
1114:                        break;
1115:                    default:
1116:                        jj_la1[8] = jj_gen;
1117:                        jj_consume_token(-1);
1118:                        throw new ParseException();
1119:                    }
1120:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1121:                    case FUZZY_SLOP:
1122:                        fuzzySlop = jj_consume_token(FUZZY_SLOP);
1123:                        fuzzy = true;
1124:                        break;
1125:                    default:
1126:                        jj_la1[9] = jj_gen;
1127:                        ;
1128:                    }
1129:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1130:                    case CARAT:
1131:                        jj_consume_token(CARAT);
1132:                        boost = jj_consume_token(NUMBER);
1133:                        switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1134:                        case FUZZY_SLOP:
1135:                            fuzzySlop = jj_consume_token(FUZZY_SLOP);
1136:                            fuzzy = true;
1137:                            break;
1138:                        default:
1139:                            jj_la1[10] = jj_gen;
1140:                            ;
1141:                        }
1142:                        break;
1143:                    default:
1144:                        jj_la1[11] = jj_gen;
1145:                        ;
1146:                    }
1147:                    String termImage = discardEscapeChar(term.image);
1148:                    if (wildcard) {
1149:                        q = getWildcardQuery(field, termImage);
1150:                    } else if (prefix) {
1151:                        q = getPrefixQuery(field, discardEscapeChar(term.image
1152:                                .substring(0, term.image.length() - 1)));
1153:                    } else if (fuzzy) {
1154:                        float fms = fuzzyMinSim;
1155:                        try {
1156:                            fms = Float.valueOf(fuzzySlop.image.substring(1))
1157:                                    .floatValue();
1158:                        } catch (Exception ignored) {
1159:                        }
1160:                        if (fms < 0.0f || fms > 1.0f) {
1161:                            {
1162:                                if (true)
1163:                                    throw new ParseException(
1164:                                            "Minimum similarity for a FuzzyQuery has to be between 0.0f and 1.0f !");
1165:                            }
1166:                        }
1167:                        q = getFuzzyQuery(field, termImage, fms);
1168:                    } else {
1169:                        q = getFieldQuery(field, termImage);
1170:                    }
1171:                    break;
1172:                case RANGEIN_START:
1173:                    jj_consume_token(RANGEIN_START);
1174:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1175:                    case RANGEIN_GOOP:
1176:                        goop1 = jj_consume_token(RANGEIN_GOOP);
1177:                        break;
1178:                    case RANGEIN_QUOTED:
1179:                        goop1 = jj_consume_token(RANGEIN_QUOTED);
1180:                        break;
1181:                    default:
1182:                        jj_la1[12] = jj_gen;
1183:                        jj_consume_token(-1);
1184:                        throw new ParseException();
1185:                    }
1186:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1187:                    case RANGEIN_TO:
1188:                        jj_consume_token(RANGEIN_TO);
1189:                        break;
1190:                    default:
1191:                        jj_la1[13] = jj_gen;
1192:                        ;
1193:                    }
1194:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1195:                    case RANGEIN_GOOP:
1196:                        goop2 = jj_consume_token(RANGEIN_GOOP);
1197:                        break;
1198:                    case RANGEIN_QUOTED:
1199:                        goop2 = jj_consume_token(RANGEIN_QUOTED);
1200:                        break;
1201:                    default:
1202:                        jj_la1[14] = jj_gen;
1203:                        jj_consume_token(-1);
1204:                        throw new ParseException();
1205:                    }
1206:                    jj_consume_token(RANGEIN_END);
1207:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1208:                    case CARAT:
1209:                        jj_consume_token(CARAT);
1210:                        boost = jj_consume_token(NUMBER);
1211:                        break;
1212:                    default:
1213:                        jj_la1[15] = jj_gen;
1214:                        ;
1215:                    }
1216:                    if (goop1.kind == RANGEIN_QUOTED) {
1217:                        goop1.image = goop1.image.substring(1, goop1.image
1218:                                .length() - 1);
1219:                    }
1220:                    if (goop2.kind == RANGEIN_QUOTED) {
1221:                        goop2.image = goop2.image.substring(1, goop2.image
1222:                                .length() - 1);
1223:                    }
1224:                    q = getRangeQuery(field, discardEscapeChar(goop1.image),
1225:                            discardEscapeChar(goop2.image), true);
1226:                    break;
1227:                case RANGEEX_START:
1228:                    jj_consume_token(RANGEEX_START);
1229:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1230:                    case RANGEEX_GOOP:
1231:                        goop1 = jj_consume_token(RANGEEX_GOOP);
1232:                        break;
1233:                    case RANGEEX_QUOTED:
1234:                        goop1 = jj_consume_token(RANGEEX_QUOTED);
1235:                        break;
1236:                    default:
1237:                        jj_la1[16] = jj_gen;
1238:                        jj_consume_token(-1);
1239:                        throw new ParseException();
1240:                    }
1241:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1242:                    case RANGEEX_TO:
1243:                        jj_consume_token(RANGEEX_TO);
1244:                        break;
1245:                    default:
1246:                        jj_la1[17] = jj_gen;
1247:                        ;
1248:                    }
1249:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1250:                    case RANGEEX_GOOP:
1251:                        goop2 = jj_consume_token(RANGEEX_GOOP);
1252:                        break;
1253:                    case RANGEEX_QUOTED:
1254:                        goop2 = jj_consume_token(RANGEEX_QUOTED);
1255:                        break;
1256:                    default:
1257:                        jj_la1[18] = jj_gen;
1258:                        jj_consume_token(-1);
1259:                        throw new ParseException();
1260:                    }
1261:                    jj_consume_token(RANGEEX_END);
1262:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1263:                    case CARAT:
1264:                        jj_consume_token(CARAT);
1265:                        boost = jj_consume_token(NUMBER);
1266:                        break;
1267:                    default:
1268:                        jj_la1[19] = jj_gen;
1269:                        ;
1270:                    }
1271:                    if (goop1.kind == RANGEEX_QUOTED) {
1272:                        goop1.image = goop1.image.substring(1, goop1.image
1273:                                .length() - 1);
1274:                    }
1275:                    if (goop2.kind == RANGEEX_QUOTED) {
1276:                        goop2.image = goop2.image.substring(1, goop2.image
1277:                                .length() - 1);
1278:                    }
1279:
1280:                    q = getRangeQuery(field, discardEscapeChar(goop1.image),
1281:                            discardEscapeChar(goop2.image), false);
1282:                    break;
1283:                case QUOTED:
1284:                    term = jj_consume_token(QUOTED);
1285:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1286:                    case FUZZY_SLOP:
1287:                        fuzzySlop = jj_consume_token(FUZZY_SLOP);
1288:                        break;
1289:                    default:
1290:                        jj_la1[20] = jj_gen;
1291:                        ;
1292:                    }
1293:                    switch ((jj_ntk == -1) ? jj_ntk() : jj_ntk) {
1294:                    case CARAT:
1295:                        jj_consume_token(CARAT);
1296:                        boost = jj_consume_token(NUMBER);
1297:                        break;
1298:                    default:
1299:                        jj_la1[21] = jj_gen;
1300:                        ;
1301:                    }
1302:                    int s = phraseSlop;
1303:
1304:                    if (fuzzySlop != null) {
1305:                        try {
1306:                            s = Float.valueOf(fuzzySlop.image.substring(1))
1307:                                    .intValue();
1308:                        } catch (Exception ignored) {
1309:                        }
1310:                    }
1311:                    q = getFieldQuery(field, discardEscapeChar(term.image
1312:                            .substring(1, term.image.length() - 1)), s);
1313:                    break;
1314:                default:
1315:                    jj_la1[22] = jj_gen;
1316:                    jj_consume_token(-1);
1317:                    throw new ParseException();
1318:                }
1319:                if (boost != null) {
1320:                    float f = (float) 1.0;
1321:                    try {
1322:                        f = Float.valueOf(boost.image).floatValue();
1323:                    } catch (Exception ignored) {
1324:                        /* Should this be handled somehow? (defaults to "no boost", if
1325:                         * boost number is invalid)
1326:                         */
1327:                    }
1328:
1329:                    // avoid boosting null queries, such as those caused by stop words
1330:                    if (q != null) {
1331:                        q.setBoost(f);
1332:                    }
1333:                }
1334:                {
1335:                    if (true)
1336:                        return q;
1337:                }
1338:                throw new Error("Missing return statement in function");
1339:            }
1340:
1341:            final private boolean jj_2_1(int xla) {
1342:                jj_la = xla;
1343:                jj_lastpos = jj_scanpos = token;
1344:                try {
1345:                    return !jj_3_1();
1346:                } catch (LookaheadSuccess ls) {
1347:                    return true;
1348:                } finally {
1349:                    jj_save(0, xla);
1350:                }
1351:            }
1352:
1353:            final private boolean jj_3R_2() {
1354:                if (jj_scan_token(TERM))
1355:                    return true;
1356:                if (jj_scan_token(COLON))
1357:                    return true;
1358:                return false;
1359:            }
1360:
1361:            final private boolean jj_3_1() {
1362:                Token xsp;
1363:                xsp = jj_scanpos;
1364:                if (jj_3R_2()) {
1365:                    jj_scanpos = xsp;
1366:                    if (jj_3R_3())
1367:                        return true;
1368:                }
1369:                return false;
1370:            }
1371:
1372:            final private boolean jj_3R_3() {
1373:                if (jj_scan_token(STAR))
1374:                    return true;
1375:                if (jj_scan_token(COLON))
1376:                    return true;
1377:                return false;
1378:            }
1379:
1380:            public QueryParserTokenManager token_source;
1381:            public Token token, jj_nt;
1382:            private int jj_ntk;
1383:            private Token jj_scanpos, jj_lastpos;
1384:            private int jj_la;
1385:            public boolean lookingAhead = false;
1386:            private boolean jj_semLA;
1387:            private int jj_gen;
1388:            final private int[] jj_la1 = new int[23];
1389:            static private int[] jj_la1_0;
1390:            static private int[] jj_la1_1;
1391:            static {
1392:                jj_la1_0();
1393:                jj_la1_1();
1394:            }
1395:
1396:            private static void jj_la1_0() {
1397:                jj_la1_0 = new int[] { 0x180, 0x180, 0xe00, 0xe00, 0x1f69f80,
1398:                        0x48000, 0x10000, 0x1f69000, 0x1348000, 0x80000,
1399:                        0x80000, 0x10000, 0x18000000, 0x2000000, 0x18000000,
1400:                        0x10000, 0x80000000, 0x20000000, 0x80000000, 0x10000,
1401:                        0x80000, 0x10000, 0x1f68000, };
1402:            }
1403:
1404:            private static void jj_la1_1() {
1405:                jj_la1_1 = new int[] { 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0,
1406:                        0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x1, 0x0, 0x1,
1407:                        0x0, 0x0, 0x0, 0x0, };
1408:            }
1409:
1410:            final private JJCalls[] jj_2_rtns = new JJCalls[1];
1411:            private boolean jj_rescan = false;
1412:            private int jj_gc = 0;
1413:
1414:            public QueryParser(CharStream stream) {
1415:                token_source = new QueryParserTokenManager(stream);
1416:                token = new Token();
1417:                jj_ntk = -1;
1418:                jj_gen = 0;
1419:                for (int i = 0; i < 23; i++)
1420:                    jj_la1[i] = -1;
1421:                for (int i = 0; i < jj_2_rtns.length; i++)
1422:                    jj_2_rtns[i] = new JJCalls();
1423:            }
1424:
1425:            public void ReInit(CharStream stream) {
1426:                token_source.ReInit(stream);
1427:                token = new Token();
1428:                jj_ntk = -1;
1429:                jj_gen = 0;
1430:                for (int i = 0; i < 23; i++)
1431:                    jj_la1[i] = -1;
1432:                for (int i = 0; i < jj_2_rtns.length; i++)
1433:                    jj_2_rtns[i] = new JJCalls();
1434:            }
1435:
1436:            public QueryParser(QueryParserTokenManager tm) {
1437:                token_source = tm;
1438:                token = new Token();
1439:                jj_ntk = -1;
1440:                jj_gen = 0;
1441:                for (int i = 0; i < 23; i++)
1442:                    jj_la1[i] = -1;
1443:                for (int i = 0; i < jj_2_rtns.length; i++)
1444:                    jj_2_rtns[i] = new JJCalls();
1445:            }
1446:
1447:            public void ReInit(QueryParserTokenManager tm) {
1448:                token_source = tm;
1449:                token = new Token();
1450:                jj_ntk = -1;
1451:                jj_gen = 0;
1452:                for (int i = 0; i < 23; i++)
1453:                    jj_la1[i] = -1;
1454:                for (int i = 0; i < jj_2_rtns.length; i++)
1455:                    jj_2_rtns[i] = new JJCalls();
1456:            }
1457:
1458:            final private Token jj_consume_token(int kind)
1459:                    throws ParseException {
1460:                Token oldToken;
1461:                if ((oldToken = token).next != null)
1462:                    token = token.next;
1463:                else
1464:                    token = token.next = token_source.getNextToken();
1465:                jj_ntk = -1;
1466:                if (token.kind == kind) {
1467:                    jj_gen++;
1468:                    if (++jj_gc > 100) {
1469:                        jj_gc = 0;
1470:                        for (int i = 0; i < jj_2_rtns.length; i++) {
1471:                            JJCalls c = jj_2_rtns[i];
1472:                            while (c != null) {
1473:                                if (c.gen < jj_gen)
1474:                                    c.first = null;
1475:                                c = c.next;
1476:                            }
1477:                        }
1478:                    }
1479:                    return token;
1480:                }
1481:                token = oldToken;
1482:                jj_kind = kind;
1483:                throw generateParseException();
1484:            }
1485:
1486:            static private final class LookaheadSuccess extends java.lang.Error {
1487:            }
1488:
1489:            final private LookaheadSuccess jj_ls = new LookaheadSuccess();
1490:
1491:            final private boolean jj_scan_token(int kind) {
1492:                if (jj_scanpos == jj_lastpos) {
1493:                    jj_la--;
1494:                    if (jj_scanpos.next == null) {
1495:                        jj_lastpos = jj_scanpos = jj_scanpos.next = token_source
1496:                                .getNextToken();
1497:                    } else {
1498:                        jj_lastpos = jj_scanpos = jj_scanpos.next;
1499:                    }
1500:                } else {
1501:                    jj_scanpos = jj_scanpos.next;
1502:                }
1503:                if (jj_rescan) {
1504:                    int i = 0;
1505:                    Token tok = token;
1506:                    while (tok != null && tok != jj_scanpos) {
1507:                        i++;
1508:                        tok = tok.next;
1509:                    }
1510:                    if (tok != null)
1511:                        jj_add_error_token(kind, i);
1512:                }
1513:                if (jj_scanpos.kind != kind)
1514:                    return true;
1515:                if (jj_la == 0 && jj_scanpos == jj_lastpos)
1516:                    throw jj_ls;
1517:                return false;
1518:            }
1519:
1520:            final public Token getNextToken() {
1521:                if (token.next != null)
1522:                    token = token.next;
1523:                else
1524:                    token = token.next = token_source.getNextToken();
1525:                jj_ntk = -1;
1526:                jj_gen++;
1527:                return token;
1528:            }
1529:
1530:            final public Token getToken(int index) {
1531:                Token t = lookingAhead ? jj_scanpos : token;
1532:                for (int i = 0; i < index; i++) {
1533:                    if (t.next != null)
1534:                        t = t.next;
1535:                    else
1536:                        t = t.next = token_source.getNextToken();
1537:                }
1538:                return t;
1539:            }
1540:
1541:            final private int jj_ntk() {
1542:                if ((jj_nt = token.next) == null)
1543:                    return (jj_ntk = (token.next = token_source.getNextToken()).kind);
1544:                else
1545:                    return (jj_ntk = jj_nt.kind);
1546:            }
1547:
1548:            private java.util.Vector jj_expentries = new java.util.Vector();
1549:            private int[] jj_expentry;
1550:            private int jj_kind = -1;
1551:            private int[] jj_lasttokens = new int[100];
1552:            private int jj_endpos;
1553:
1554:            private void jj_add_error_token(int kind, int pos) {
1555:                if (pos >= 100)
1556:                    return;
1557:                if (pos == jj_endpos + 1) {
1558:                    jj_lasttokens[jj_endpos++] = kind;
1559:                } else if (jj_endpos != 0) {
1560:                    jj_expentry = new int[jj_endpos];
1561:                    for (int i = 0; i < jj_endpos; i++) {
1562:                        jj_expentry[i] = jj_lasttokens[i];
1563:                    }
1564:                    boolean exists = false;
1565:                    for (java.util.Enumeration e = jj_expentries.elements(); e
1566:                            .hasMoreElements();) {
1567:                        int[] oldentry = (int[]) (e.nextElement());
1568:                        if (oldentry.length == jj_expentry.length) {
1569:                            exists = true;
1570:                            for (int i = 0; i < jj_expentry.length; i++) {
1571:                                if (oldentry[i] != jj_expentry[i]) {
1572:                                    exists = false;
1573:                                    break;
1574:                                }
1575:                            }
1576:                            if (exists)
1577:                                break;
1578:                        }
1579:                    }
1580:                    if (!exists)
1581:                        jj_expentries.addElement(jj_expentry);
1582:                    if (pos != 0)
1583:                        jj_lasttokens[(jj_endpos = pos) - 1] = kind;
1584:                }
1585:            }
1586:
1587:            public ParseException generateParseException() {
1588:                jj_expentries.removeAllElements();
1589:                boolean[] la1tokens = new boolean[33];
1590:                for (int i = 0; i < 33; i++) {
1591:                    la1tokens[i] = false;
1592:                }
1593:                if (jj_kind >= 0) {
1594:                    la1tokens[jj_kind] = true;
1595:                    jj_kind = -1;
1596:                }
1597:                for (int i = 0; i < 23; i++) {
1598:                    if (jj_la1[i] == jj_gen) {
1599:                        for (int j = 0; j < 32; j++) {
1600:                            if ((jj_la1_0[i] & (1 << j)) != 0) {
1601:                                la1tokens[j] = true;
1602:                            }
1603:                            if ((jj_la1_1[i] & (1 << j)) != 0) {
1604:                                la1tokens[32 + j] = true;
1605:                            }
1606:                        }
1607:                    }
1608:                }
1609:                for (int i = 0; i < 33; i++) {
1610:                    if (la1tokens[i]) {
1611:                        jj_expentry = new int[1];
1612:                        jj_expentry[0] = i;
1613:                        jj_expentries.addElement(jj_expentry);
1614:                    }
1615:                }
1616:                jj_endpos = 0;
1617:                jj_rescan_token();
1618:                jj_add_error_token(0, 0);
1619:                int[][] exptokseq = new int[jj_expentries.size()][];
1620:                for (int i = 0; i < jj_expentries.size(); i++) {
1621:                    exptokseq[i] = (int[]) jj_expentries.elementAt(i);
1622:                }
1623:                return new ParseException(token, exptokseq, tokenImage);
1624:            }
1625:
1626:            final public void enable_tracing() {
1627:            }
1628:
1629:            final public void disable_tracing() {
1630:            }
1631:
1632:            final private void jj_rescan_token() {
1633:                jj_rescan = true;
1634:                for (int i = 0; i < 1; i++) {
1635:                    JJCalls p = jj_2_rtns[i];
1636:                    do {
1637:                        if (p.gen > jj_gen) {
1638:                            jj_la = p.arg;
1639:                            jj_lastpos = jj_scanpos = p.first;
1640:                            switch (i) {
1641:                            case 0:
1642:                                jj_3_1();
1643:                                break;
1644:                            }
1645:                        }
1646:                        p = p.next;
1647:                    } while (p != null);
1648:                }
1649:                jj_rescan = false;
1650:            }
1651:
1652:            final private void jj_save(int index, int xla) {
1653:                JJCalls p = jj_2_rtns[index];
1654:                while (p.gen > jj_gen) {
1655:                    if (p.next == null) {
1656:                        p = p.next = new JJCalls();
1657:                        break;
1658:                    }
1659:                    p = p.next;
1660:                }
1661:                p.gen = jj_gen + xla - jj_la;
1662:                p.first = token;
1663:                p.arg = xla;
1664:            }
1665:
1666:            static final class JJCalls {
1667:                int gen;
1668:                Token first;
1669:                int arg;
1670:                JJCalls next;
1671:            }
1672:
1673:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.