Search in sources :

Example 11 with IPatternSequence

use of org.matheclipse.core.interfaces.IPatternSequence in project symja_android_library by axkr.

the class PatternMatcher method matchAST.

protected boolean matchAST(IAST lhsPatternAST, final IExpr lhsEvalExpr, EvalEngine engine, StackMatcher stackMatcher) {
    if (lhsEvalExpr instanceof IAST) {
        if (lhsPatternAST.isFreeOfPatterns() && lhsPatternAST.equals(lhsEvalExpr)) {
            return stackMatcher.matchRest();
        }
        IAST lhsEvalAST = (IAST) lhsEvalExpr;
        final ISymbol sym = lhsPatternAST.topHead();
        if (lhsPatternAST.size() <= lhsEvalAST.size()) {
            if (lhsPatternAST.isOrderlessAST()) {
                IExpr temp = fPatternMap.substituteASTPatternOrSymbols(lhsPatternAST, false).orElse(lhsPatternAST);
                if (temp.isAST(lhsPatternAST.head())) {
                    lhsPatternAST = (IAST) temp;
                    IAST[] removed = removeOrderless(lhsPatternAST, lhsEvalAST);
                    if (removed == null) {
                        return false;
                    }
                    lhsPatternAST = removed[0];
                    lhsEvalAST = removed[1];
                }
            } else if (lhsPatternAST.isFlatAST()) {
                IExpr temp = fPatternMap.substituteASTPatternOrSymbols(lhsPatternAST, false).orElse(lhsPatternAST);
                if (temp.isAST(lhsPatternAST.head())) {
                    IAST[] removed = removeFlat((IAST) temp, lhsEvalAST);
                    if (removed == null) {
                        return false;
                    }
                    lhsPatternAST = removed[0];
                    lhsEvalAST = removed[1];
                }
            }
            if ((lhsPatternAST.isFlatAST()) && sym.equals(lhsEvalAST.topHead()) && !(lhsPatternAST.isOrderlessAST() && lhsPatternAST.size() == lhsEvalAST.size())) {
                if (!matchHeads(lhsPatternAST, lhsEvalAST, engine)) {
                    return false;
                }
                if (lhsPatternAST.size() == 1 && lhsEvalAST.size() == 1) {
                    return stackMatcher.matchRest();
                }
                return matchFlatAndFlatOrderless(sym, lhsPatternAST, lhsEvalAST, engine, stackMatcher);
            }
        }
        int lhsEvalSize = lhsEvalAST.size();
        if (lhsPatternAST.isEvalFlagOn(IAST.CONTAINS_PATTERN_SEQUENCE)) {
            if (!matchHeads(lhsPatternAST, lhsEvalAST, engine)) {
                return false;
            }
            if (lhsPatternAST.isEmpty() && lhsEvalAST.isEmpty()) {
                return stackMatcher.matchRest();
            }
            final int lastPosition = lhsPatternAST.argSize();
            if (lastPosition == 1 && lhsPatternAST.get(lastPosition).isAST(S.PatternTest, 3)) {
                if (lhsPatternAST.size() <= lhsEvalSize) {
                    IAST patternTest = (IAST) lhsPatternAST.get(lastPosition);
                    if (patternTest.arg1().isPatternSequence(false)) {
                        // TODO only the special case, where the last element is
                        // a pattern sequence, is handled here
                        IASTAppendable seq = F.Sequence();
                        seq.appendAll(lhsEvalAST, lastPosition, lhsEvalSize);
                        if (((IPatternSequence) patternTest.arg1()).matchPatternSequence(seq, fPatternMap, lhsPatternAST.topHead())) {
                            if (matchAST(lhsPatternAST.removeFromEnd(lastPosition), lhsEvalAST.removeFromEnd(lastPosition), engine, stackMatcher)) {
                                return fPatternMap.isPatternTest(patternTest.arg1(), patternTest.arg2(), engine);
                            }
                            return false;
                        }
                    }
                }
            } else if (lhsPatternAST.size() > 1 && lhsPatternAST.arg1().isPatternSequence(false)) {
                IPatternSequence patternSequence = (IPatternSequence) lhsPatternAST.arg1();
                return matchBlankSequence(patternSequence, lhsPatternAST, 1, lhsEvalAST, engine, stackMatcher);
            } else {
                if (lhsPatternAST.size() > 1 && lhsEvalSize > 1) {
                    if (matchExpr(lhsPatternAST.arg1(), lhsEvalAST.arg1(), engine)) {
                        return matchAST(lhsPatternAST.rest().addEvalFlags(IAST.CONTAINS_PATTERN_SEQUENCE), lhsEvalAST.rest(), engine, stackMatcher);
                    }
                }
            }
            return false;
        }
        if (lhsPatternAST.size() != lhsEvalSize || !matchHeads(lhsPatternAST, lhsEvalAST, engine)) {
            return false;
        }
        if (lhsPatternAST.isOrderlessAST() && lhsPatternAST.size() > 2) {
            // only "pure Orderless" and "FlatOrderless with same size()" will be handled here:
            OrderlessStepVisitor visitor = new OrderlessStepVisitor(sym, lhsPatternAST, lhsEvalAST, stackMatcher, fPatternMap, (sym.hasOneIdentityAttribute() || sym.hasFlatAttribute()) || // same size ==> use OneIdentity in pattern matching
            (lhsPatternAST.size() == lhsEvalSize && !sym.hasFlatAttribute()));
            MultisetPartitionsIterator iter = new MultisetPartitionsIterator(visitor, lhsPatternAST.argSize());
            return !iter.execute();
        }
        return matchASTSequence(lhsPatternAST, lhsEvalAST, 0, engine, stackMatcher);
    }
    return false;
}
Also used : ISymbol(org.matheclipse.core.interfaces.ISymbol) IASTAppendable(org.matheclipse.core.interfaces.IASTAppendable) MultisetPartitionsIterator(org.matheclipse.core.combinatoric.MultisetPartitionsIterator) IPatternSequence(org.matheclipse.core.interfaces.IPatternSequence) IAST(org.matheclipse.core.interfaces.IAST) IExpr(org.matheclipse.core.interfaces.IExpr)

Aggregations

IPatternSequence (org.matheclipse.core.interfaces.IPatternSequence)11 IAST (org.matheclipse.core.interfaces.IAST)7 IExpr (org.matheclipse.core.interfaces.IExpr)5 IPatternObject (org.matheclipse.core.interfaces.IPatternObject)5 IASTAppendable (org.matheclipse.core.interfaces.IASTAppendable)4 ISymbol (org.matheclipse.core.interfaces.ISymbol)3 MultisetPartitionsIterator (org.matheclipse.combinatoric.MultisetPartitionsIterator)2 Serializable (java.io.Serializable)1 Comparator (java.util.Comparator)1 BiPredicate (java.util.function.BiPredicate)1 Predicate (java.util.function.Predicate)1 NumberPartitionsIterator (org.matheclipse.combinatoric.NumberPartitionsIterator)1 MultisetPartitionsIterator (org.matheclipse.core.combinatoric.MultisetPartitionsIterator)1 NumberPartitionsIterator (org.matheclipse.core.combinatoric.NumberPartitionsIterator)1 EvalEngine (org.matheclipse.core.eval.EvalEngine)1 F (org.matheclipse.core.expression.F)1 IBuiltInSymbol (org.matheclipse.core.interfaces.IBuiltInSymbol)1 IEvaluator (org.matheclipse.core.interfaces.IEvaluator)1 IPattern (org.matheclipse.core.interfaces.IPattern)1 IRational (org.matheclipse.core.interfaces.IRational)1