Search in sources :

Example 1 with IPatternObject

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

the class PatternMap method determinePatternsRecursive.

/**
	 * Determine all patterns (i.e. all objects of instance IPattern) in the
	 * given expression
	 * 
	 * Increments this classes pattern counter.
	 * 
	 * @param patternIndexMap
	 * @param lhsPatternExpr
	 *            the (left-hand-side) expression which could contain pattern
	 *            objects.
	 * @param treeLevel
	 *            TODO
	 */
private int determinePatternsRecursive(Map<IExpr, Integer> patternIndexMap, final IAST lhsPatternExpr, int treeLevel) {
    final IAST ast = lhsPatternExpr;
    if (lhsPatternExpr.isAST(F.Except, 2, 3)) {
        fRuleWithoutPattern = false;
    }
    int listEvalFlags = IAST.NO_FLAG;
    for (int i = 0; i < ast.size(); i++) {
        IExpr temp = ast.get(i);
        if (temp.isAST()) {
            listEvalFlags |= determinePatternsRecursive(patternIndexMap, (IAST) temp, treeLevel + 1);
            fPriority -= 11;
        } else if (temp instanceof IPatternObject) {
            int[] result = ((IPatternObject) temp).addPattern(this, patternIndexMap);
            listEvalFlags |= result[0];
            fPriority -= result[1];
        } else {
            fPriority -= (50 - treeLevel);
        }
    }
    ast.setEvalFlags(listEvalFlags);
    //		listEvalFlags &= IAST.CONTAINS_NO_DEFAULT_PATTERN_MASK;
    return listEvalFlags;
}
Also used : IPatternObject(org.matheclipse.core.interfaces.IPatternObject) IAST(org.matheclipse.core.interfaces.IAST) IExpr(org.matheclipse.core.interfaces.IExpr)

Example 2 with IPatternObject

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

the class PatternSequence method equivalent.

/**
	 * Check if the two left-hand-side pattern expressions are equivalent. (i.e.
	 * <code>f[x_,y_]</code> is equivalent to <code>f[a_,b_]</code> )
	 * 
	 * @param patternExpr2
	 * @param pm1
	 * @param pm2
	 * @return
	 */
@Override
public boolean equivalent(final IPatternObject patternExpr2, final PatternMap pm1, PatternMap pm2) {
    if (this == patternExpr2) {
        return true;
    }
    if (patternExpr2 instanceof PatternSequence) {
        // test if the pattern indices are equal
        final IPatternSequence p2 = (IPatternSequence) patternExpr2;
        if (getIndex(pm1) != p2.getIndex(pm2)) {
            return false;
        }
        // test if the "check" expressions are equal
        final Object o1 = getCondition();
        final Object o2 = p2.getCondition();
        if ((o1 == null) || (o2 == null)) {
            return o1 == o2;
        }
        return o1.equals(o2);
    }
    return false;
}
Also used : IPatternSequence(org.matheclipse.core.interfaces.IPatternSequence) IPatternSequence(org.matheclipse.core.interfaces.IPatternSequence) IPatternObject(org.matheclipse.core.interfaces.IPatternObject)

Example 3 with IPatternObject

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

the class PatternMatcher method equivalent.

/**
	 * Check if the two left-hand-side pattern expressions are equivalent. (i.e. <code>f[x_,y_]</code> is equivalent to
	 * <code>f[a_,b_]</code> )
	 * 
	 * @param patternExpr1
	 * @param patternExpr2
	 * @param pm1
	 * @param pm2
	 * @return
	 */
public static boolean equivalent(final IExpr patternExpr1, final IExpr patternExpr2, final PatternMap pm1, PatternMap pm2) {
    if (patternExpr1 == patternExpr2) {
        return true;
    }
    if (!patternExpr1.isPatternExpr()) {
        if (!patternExpr2.isPatternExpr()) {
            return patternExpr1.equals(patternExpr2);
        }
        return false;
    }
    if (patternExpr1.isAST()) {
        if (patternExpr2.isAST()) {
            final IAST l1 = (IAST) patternExpr1;
            final IAST l2 = (IAST) patternExpr2;
            if (l1.size() != l2.size()) {
                return false;
            }
            IExpr temp1, temp2;
            for (int i = 0; i < l1.size(); i++) {
                temp1 = l1.get(i);
                temp2 = l2.get(i);
                if (temp1 == temp2) {
                    continue;
                }
                if (temp1.hashCode() != temp2.hashCode()) {
                    if (temp1.isPatternExpr() && temp2.isPatternExpr()) {
                        if (!equivalent(temp1, temp2, pm1, pm2)) {
                            return false;
                        } else {
                            continue;
                        }
                    }
                    return false;
                }
                if (!temp1.isPatternExpr() || !temp2.isPatternExpr()) {
                    if (!temp1.equals(temp2)) {
                        return false;
                    }
                }
                if (!equivalent(temp1, temp2, pm1, pm2)) {
                    return false;
                }
            }
            return true;
        }
        return false;
    }
    if (patternExpr1 instanceof IPatternObject) {
        if (patternExpr2 instanceof IPatternObject) {
            return ((IPatternObject) patternExpr1).equivalent((IPatternObject) patternExpr2, pm1, pm2);
        }
        return false;
    }
    return patternExpr1.equals(patternExpr2);
}
Also used : IPatternObject(org.matheclipse.core.interfaces.IPatternObject) IAST(org.matheclipse.core.interfaces.IAST) IExpr(org.matheclipse.core.interfaces.IExpr)

Example 4 with IPatternObject

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

the class EvalEngine method evalASTArg1.

/**
 * Evaluate an AST with only one argument (i.e. <code>head[arg1]</code>). The evaluation steps are
 * controlled by the header attributes.
 *
 * @param ast
 * @return
 */
private IExpr evalASTArg1(final IAST ast) {
    // special case ast.isAST1()
    // head == ast[0] --- arg1 == ast[1]
    IExpr result = ast.head().evaluateHead(ast, this);
    if (result.isPresent()) {
        return result;
    }
    final ISymbol symbol = ast.topHead();
    final int attributes = symbol.getAttributes();
    if ((attributes & ISymbol.SEQUENCEHOLD) != ISymbol.SEQUENCEHOLD) {
        if ((result = F.flattenSequence(ast)).isPresent()) {
            return result;
        }
    }
    if ((result = evalArgs(ast, attributes)).isPresent()) {
        return result;
    }
    final IExpr arg1 = ast.arg1();
    if (ISymbol.hasFlatAttribute(attributes)) {
        if (arg1.head().equals(symbol)) {
            // associative
            return arg1;
        }
        if (arg1.isUnevaluated() && arg1.first().head().equals(symbol) && arg1.first().isAST()) {
            IAST unevaluated = (IAST) arg1.first();
            return unevaluated.map(symbol, x -> F.Unevaluated(x));
        }
    }
    if ((ISymbol.LISTABLE & attributes) == ISymbol.LISTABLE) {
        if (symbol.isBuiltInSymbol()) {
            if (arg1.isRealVector() && ((IAST) arg1).size() > 1) {
                final IEvaluator module = ((IBuiltInSymbol) symbol).getEvaluator();
                if (module instanceof DoubleUnaryOperator) {
                    DoubleUnaryOperator oper = (DoubleUnaryOperator) module;
                    return ASTRealVector.map((IAST) arg1, oper);
                }
            } else if (arg1.isRealMatrix()) {
                final IEvaluator module = ((IBuiltInSymbol) symbol).getEvaluator();
                if (module instanceof DoubleUnaryOperator) {
                    DoubleUnaryOperator oper = (DoubleUnaryOperator) module;
                    return ASTRealMatrix.map((IAST) arg1, oper);
                }
            }
            if (arg1.isList()) {
                // thread over the list
                return EvalAttributes.threadList(ast, S.List, ast.head(), ((IAST) arg1).argSize());
            } else if (arg1.isAssociation()) {
                // thread over the association
                return ((IAssociation) arg1).mapThread(ast, 1);
            } else if (arg1.isSparseArray()) {
                return ((ISparseArray) arg1).mapThread(ast, 1);
            } else if (arg1.isConditionalExpression()) {
                IExpr temp = ast.extractConditionalExpression(true);
                if (temp.isPresent()) {
                    return temp;
                }
            }
        }
    }
    if ((ISymbol.NUMERICFUNCTION & attributes) == ISymbol.NUMERICFUNCTION) {
        if (ast.arg1().isIndeterminate()) {
            return S.Indeterminate;
        }
    }
    if (!(arg1 instanceof IPatternObject) && arg1.isPresent()) {
        ISymbol lhsSymbol = arg1.isSymbol() ? (ISymbol) arg1 : arg1.topHead();
        return lhsSymbol.evalUpRules(ast, this);
    }
    return F.NIL;
}
Also used : IBuiltInSymbol(org.matheclipse.core.interfaces.IBuiltInSymbol) IEvaluator(org.matheclipse.core.interfaces.IEvaluator) ISparseArray(org.matheclipse.core.interfaces.ISparseArray) ISymbol(org.matheclipse.core.interfaces.ISymbol) IPatternObject(org.matheclipse.core.interfaces.IPatternObject) IExpr(org.matheclipse.core.interfaces.IExpr) IAST(org.matheclipse.core.interfaces.IAST) DoubleUnaryOperator(java.util.function.DoubleUnaryOperator)

Example 5 with IPatternObject

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

the class EvalEngine method evalSetAttributesRecursive.

private IExpr evalSetAttributesRecursive(IAST ast, boolean noEvaluation, boolean evalNumericFunction, int level) {
    // final ISymbol symbol = ast.topHead();
    IExpr head = ast.head();
    if (!(head instanceof IPatternObject) && !noEvaluation) {
        IExpr headResult = head.evaluate(this);
        if (headResult.isPresent()) {
            ast = ast.apply(headResult);
            head = headResult;
        }
    }
    ISymbol symbol = head.topHead();
    if (head.isSymbol()) {
        symbol = (ISymbol) head;
    }
    if (symbol.isBuiltInSymbol()) {
        // call so that attributes may be set in
        // AbstractFunctionEvaluator#setUp() method
        ((IBuiltInSymbol) symbol).getEvaluator();
    }
    int headID = ast.headID();
    if (headID >= 0) {
        if (headID == ID.Blank || headID == ID.BlankSequence || headID == ID.BlankNullSequence || headID == ID.Pattern || headID == ID.Optional || headID == ID.OptionsPattern || headID == ID.Repeated || headID == ID.RepeatedNull) {
            return ((IFunctionEvaluator) ((IBuiltInSymbol) ast.head()).getEvaluator()).evaluate(ast, this);
        }
    }
    final int attributes = symbol.getAttributes();
    IASTMutable resultList = F.NIL;
    if ((ISymbol.HOLDALL & attributes) != ISymbol.HOLDALL) {
        final int astSize = ast.size();
        if ((ISymbol.HOLDFIRST & attributes) == ISymbol.NOATTRIBUTE) {
            // the HoldFirst attribute isn't set here
            if (astSize > 1) {
                IExpr expr = ast.arg1();
                if (expr.isAST()) {
                    resultList = evalSetAttributeArg(ast, 1, (IAST) expr, resultList, noEvaluation, level);
                } else if (!(expr instanceof IPatternObject) && !noEvaluation) {
                    IExpr temp = expr.evaluate(this);
                    if (temp.isPresent()) {
                        resultList = ast.setAtCopy(1, temp);
                    }
                }
            }
        }
        if (astSize > 2) {
            if ((ISymbol.HOLDREST & attributes) == ISymbol.NOATTRIBUTE) {
                // the HoldRest attribute isn't set here
                for (int i = 2; i < astSize; i++) {
                    IExpr expr = ast.get(i);
                    if (expr.isAST()) {
                        resultList = evalSetAttributeArg(ast, i, (IAST) expr, resultList, noEvaluation, level);
                    } else if (!(expr instanceof IPatternObject) && !noEvaluation) {
                        IExpr temp = expr.evaluate(this);
                        if (temp.isPresent()) {
                            if (resultList.isPresent()) {
                                resultList.set(i, temp);
                            } else {
                                resultList = ast.setAtCopy(i, temp);
                            }
                        }
                    }
                }
            }
        }
        if (evalNumericFunction && ((ISymbol.HOLDALL & attributes) == ISymbol.NOATTRIBUTE)) {
            IAST f = resultList.orElse(ast);
            if (f.isNumericFunction(true)) {
                IExpr temp = evalLoop(f);
                if (temp.isPresent()) {
                    return temp;
                }
            }
        }
    }
    if (resultList.isPresent()) {
        if (resultList.size() > 2) {
            if (ISymbol.hasFlatAttribute(attributes)) {
                // associative
                IASTAppendable result;
                if ((result = EvalAttributes.flattenDeep(resultList)).isPresent()) {
                    return evalSetOrderless(result, attributes, noEvaluation, level);
                }
            }
            IExpr expr = evalSetOrderless(resultList, attributes, noEvaluation, level);
            if (expr.isPresent()) {
                return expr;
            }
        }
        return resultList;
    }
    if ((ast.getEvalFlags() & IAST.IS_FLATTENED_OR_SORTED_MASK) != 0x0000) {
        // already flattened or sorted
        return ast;
    }
    if (ISymbol.hasFlatAttribute(attributes)) {
        // associative
        IASTAppendable result;
        if ((result = EvalAttributes.flattenDeep(ast)).isPresent()) {
            return evalSetOrderless(result, attributes, noEvaluation, level);
        }
    }
    return evalSetOrderless(ast, attributes, noEvaluation, level);
}
Also used : IBuiltInSymbol(org.matheclipse.core.interfaces.IBuiltInSymbol) ISymbol(org.matheclipse.core.interfaces.ISymbol) IFunctionEvaluator(org.matheclipse.core.eval.interfaces.IFunctionEvaluator) IASTAppendable(org.matheclipse.core.interfaces.IASTAppendable) IPatternObject(org.matheclipse.core.interfaces.IPatternObject) IExpr(org.matheclipse.core.interfaces.IExpr) IASTMutable(org.matheclipse.core.interfaces.IASTMutable) IAST(org.matheclipse.core.interfaces.IAST)

Aggregations

IPatternObject (org.matheclipse.core.interfaces.IPatternObject)22 IExpr (org.matheclipse.core.interfaces.IExpr)17 IAST (org.matheclipse.core.interfaces.IAST)16 ISymbol (org.matheclipse.core.interfaces.ISymbol)8 IPatternSequence (org.matheclipse.core.interfaces.IPatternSequence)6 IASTAppendable (org.matheclipse.core.interfaces.IASTAppendable)5 IASTMutable (org.matheclipse.core.interfaces.IASTMutable)4 PatternNested (org.matheclipse.core.expression.PatternNested)3 IAssociation (org.matheclipse.core.interfaces.IAssociation)3 INumber (org.matheclipse.core.interfaces.INumber)3 ISignedNumber (org.matheclipse.core.interfaces.ISignedNumber)3 OptionsPattern (org.matheclipse.core.expression.OptionsPattern)2 Pattern (org.matheclipse.core.expression.Pattern)2 IBuiltInSymbol (org.matheclipse.core.interfaces.IBuiltInSymbol)2 IComplex (org.matheclipse.core.interfaces.IComplex)2 IComplexNum (org.matheclipse.core.interfaces.IComplexNum)2 IFraction (org.matheclipse.core.interfaces.IFraction)2 InfixOperator (org.matheclipse.parser.client.operator.InfixOperator)2 Operator (org.matheclipse.parser.client.operator.Operator)2 PostfixOperator (org.matheclipse.parser.client.operator.PostfixOperator)2