⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 logikusparser.java

📁 国外的一套开源CRM
💻 JAVA
📖 第 1 页 / 共 2 页
字号:
/*
 * $Id: LogikusParser.java,v 1.1 2003/08/19 01:12:57 jonesde Exp $
 *
 * Copyright (c) 1999 Steven J. Metsker.
 * Copyright (c) 2001 The Open For Business Project - www.ofbiz.org
 *
 *  Permission is hereby granted, free of charge, to any person obtaining a
 *  copy of this software and associated documentation files (the "Software"),
 *  to deal in the Software without restriction, including without limitation
 *  the rights to use, copy, modify, merge, publish, distribute, sublicense,
 *  and/or sell copies of the Software, and to permit persons to whom the
 *  Software is furnished to do so, subject to the following conditions:
 *
 *  The above copyright notice and this permission notice shall be included
 *  in all copies or substantial portions of the Software.
 *
 *  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
 *  OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
 *  MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
 *  IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
 *  CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT
 *  OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR
 *  THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 */

package org.ofbiz.rules.logikus;


import org.ofbiz.rules.parse.*;
import org.ofbiz.rules.parse.tokens.*;


/**
 * <p>This class provides a parser for Logikus, a logic
 * language similar to Prolog.
 * <p>The grammar this class supports is:
 * <blockquote><pre>
 *
 * <old> <!-- note: this is the original grammar, see the current one below -->
 *     structure    = functor ('(' commaList(term) ')' | Empty);
 *     functor      = '.' | LowercaseWord | QuotedString;
 *     term         = structure | Num | list | variable;
 *     variable     = UppercaseWord | '_';
 *     factor       = '(' expression ')' | Num | variable;
 * </old>
 *
 *     axiom        = structure (ruleDef | Empty);
 *     structure    = functor ('(' commaList(term) ')');
 *     functor      = '.' | LowercaseWord | UppercaseWord;
 *     term         = structure | Num | QuotedString | list | variable;
 *     variable     = LowercaseWord | UppercaseWord | '_';
 * <br>
 *     ruleDef      = ":-" commaList(condition);
 *     condition    = structure | not | evaluation | comparison | list;
 * <br>
 *     not          = "not" structure ;
 * <br>
 *     evaluation   =      '#' '(' arg ',' arg ')';
 *     comparison   = operator '(' arg ',' arg ')';
 *     arg          = expression | functor;
 *     operator     = '<' | '>' | '=' | "<=" | ">=" | "!=" ;
 *     expression   = phrase ('+' phrase | '-' phrase)*;
 *     phrase       = factor ('*' factor | '/' factor)*;
 *     factor       = '(' expression ')' | Num | QuotedString | variable;
 * <br>
 *     list         = '[' (listContents | Empty) ']';
 *     listContents = commaList(term) listTail;
 *     listTail     = ('|' (variable | list)) | Empty;
 * <br>
 *     commaList(p) = p (',' p)*;
 * </pre></blockquote>
 *
 * The following program and query use most of the features of
 * the Logikus grammar:
 *
 * <blockquote><pre>
 *     // program
 *     member(X, [X | Rest]);
 *     member(X, [Y | Rest]) :- member(X, Rest);
 *     primes([2, 3, 5, 7, 11, 13]);
 *     factor(X, P, Q) :-
 *         primes(Primes),
 *         member(P, Primes), member(Q, Primes), =(P*Q, X);
 * <br>
 *     // query
 *     factor(91, A, B)
 * <br>
 *     // results
 *     A = 7.0, B = 13.0
 *     A = 13.0, B = 7.0
 *     no
 * </pre></blockquote>
 *
 * The class <code>LogikusFacade</code> simplifies the
 * construction of <code>Program</code> and <code>Query</code>
 * objects from the text given above. A Java program can prove
 * the query to generate the results.
 *
 * <p>
 * The class <code>LogikusIde</code> is an example of using the
 * <code>Logikus</code> parser in practice. It uses
 * <code>LogikusFacade</code> to create a <code>Query</code>,
 * proves the query, and displays the query's variables for
 * each proof. As in Prolog, the Logikus development
 * environment prints "no" when no further proofs remain.
 *
 * @author Steven J. Metsker
 * @version 1.0
 */
public class LogikusParser {
    protected Sequence structure;
    protected Sequence expression;
    protected Sequence list;

    /**
     * Return a parser that recognizes the grammar:
     *
     *    arg = expression | functor;
     */
    protected Parser arg() {
        Alternation a = new Alternation();

        a.add(expression());
        a.add(functor().setAssembler(new AtomAssembler()));
        return a;
    }

    /**
     * Return a parser that recognizes the grammar:
     *
     * <blockquote><pre>
     *    axiom = structure (ruleDef | Empty);
     * </pre></blockquote>
     *
     * @return a parser that recognizes an axiom
     */
    public Parser axiom() {
        Sequence s = new Sequence("axiom");

        s.add(structure());
        Alternation a = new Alternation();

        a.add(ruleDef());
        a.add(new Empty());
        s.add(a);

        s.setAssembler(new AxiomAssembler());
        return s;
    }

    /**
     * Using the given parser, this method composes a new
     * parser with the grammar:
     *
     *     commaList(p) = p (',' p)*;
     *
     * The Logikus language uses this construction several
     * times.
     */
    protected static Sequence commaList(Parser p) {
        Sequence commaP = new Track();

        commaP.add(new Symbol(',').discard());
        commaP.add(p);

        Sequence s = new Sequence();

        s.add(p);
        s.add(new Repetition(commaP));
        return s;
    }

    /**
     * Return a parser that recognizes the grammar:
     *
     * <blockquote><pre>
     *    comparison = operator '(' arg ',' arg ')';
     * </pre></blockquote>
     *
     * @return a parser that recognizes a comparison
     */
    public Sequence comparison() {
        Track t = new Track("comparison");

        t.add(operator());
        t.add(new Symbol('(').discard());
        t.add(arg());
        t.add(new Symbol(',').discard());
        t.add(arg());
        t.add(new Symbol(')').discard());
        t.setAssembler(new ComparisonAssembler());
        return t;
    }

    /**
     * Return a parser that recognizes the grammar:
     *
     * <blockquote><pre>
     *    condition = structure | not | evaluation | comparison |
     *                list;
     * </pre></blockquote>
     *
     * @return a parser that recognizes a condition
     */
    public Alternation condition() {
        Alternation a = new Alternation("condition");

        a.add(structure());
        a.add(not());
        a.add(evaluation());
        a.add(comparison());
        a.add(list());
        return a;
    }

    /**
     * Return a parser that recognizes the grammar:
     *
     *    divideFactor = '/' factor;
     */
    protected Parser divideFactor() {
        Sequence s = new Sequence("divideFactor");

        s.add(new Symbol('/').discard());
        s.add(factor());
        s.setAssembler(new ArithmeticAssembler('/'));
        return s;
    }

    /**
     * Return a parser that recognizes the grammar:
     *
     *     evaluation = '#' '(' arg ',' arg ')';
     *
     * For example, this parser will recognize
     * "#(X, 12321/111)", translating it to an Evaluation
     * object. When asked to prove itself, the Evaluation
     * object will unify its first term with the value of
     * its second term.
     */
    protected Parser evaluation() {

        Track t = new Track("evaluation");

        t.add(new Symbol('#').discard());
        t.add(new Symbol('(').discard());
        t.add(arg());
        t.add(new Symbol(',').discard());
        t.add(arg());
        t.add(new Symbol(')').discard());
        t.setAssembler(new EvaluationAssembler());
        return t;
    }

    /**
     * Return a parser that recognizes the grammar:
     *
     *    expression = phrase ('+' phrase | '-' phrase)*;
     */
    protected Parser expression() {

        /*
         * This use of a static variable avoids the infinite
         * recursion inherent in the language definition.
         */
        if (expression == null) {
            expression = new Sequence("expression");
            expression.add(phrase());
            Alternation a = new Alternation();

            a.add(plusPhrase());
            a.add(minusPhrase());
            expression.add(new Repetition(a));
        }
        return expression;
    }

    /**
     * Return a parser that recognizes the grammar:
     *
     *    factor = '(' expression ')' | Num | QuotedString | variable;
     */
    protected Parser factor() {
        Alternation a = new Alternation("factor");
        Sequence s = new Sequence();

        s.add(new Symbol('(').discard());
        s.add(expression());
        s.add(new Symbol(')').discard());
        a.add(s);
        a.add(num());
        a.add(string());
        a.add(variable());
        return a;
    }

    /**
     * Return a parser that recognizes the grammar:
     *
     *    functor = '.' | LowercaseWord | UppercaseWord;
     */
    protected Parser functor() {
        Alternation a = new Alternation("functor");

        a.add(new LowercaseWord());
        a.add(new UppercaseWord());

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -