/** * var unification. * * <p>First, verify the Term eventually already unified with the same Var if the Term exist, unify * var with that term, in order to handle situation as (A = p(X) , A = p(1)) which must produce * X/1. * * <p>If instead the var is not already unified, then: * * <p>if the Term is a var bound to X, then try unification with X so for example if A=1, B=A then * B is unified to 1 and not to A (note that it's coherent with chronological backtracking: the * eventually backtracked A unification is always after backtracking of B unification. * * <p>if are the same Var, unification must succeed, but without any new bindings (to avoid cycles * for extends in A = B, B = A) * * <p>if the term is a number, then it's a success and new link is created (retractable by means * of a code) * * <p>if the term is a compound, then occur check test is executed: the var must not appear in the * compound ( avoid X=p(X), or p(X,X)=p(Y,f(Y)) ); if occur check is ok then it's success and a * new link is created (retractable by a code) */ boolean unify(List vl1, List vl2, Term t) { Term tt = getTerm(); if (tt == this) { t = t.getTerm(); if (t instanceof Var) { if (this == t) { try { vl1.add(this); } catch (NullPointerException e) { /* vl1==null mean nothing intresting for the caller */ } return true; } } else if (t instanceof Struct) { // occur-check if (occurCheck(vl2, (Struct) t)) { return false; } } else if (!(t instanceof Number)) { return false; } link = t; try { vl1.add(this); } catch (NullPointerException e) { /* vl1==null mean nothing intresting for the caller */ } // System.out.println("VAR "+name+" BOUND to "+link+" - time: "+time+" - mark: "+mark); return true; } else { return (tt.unify(vl1, vl2, t)); } }
@Override public boolean unify(Term t1) { // used to be implemented using recursion but caused stack overflow problems with long lists Term t2 = this; do { TermType tType = t1.getType(); if (tType == TermType.LIST) { if (t2.getArgument(0).unify(t1.getArgument(0)) == false) { return false; } t1 = t1.getArgument(1); t2 = t2.getArgument(1); } else if (tType.isVariable()) { return t1.unify(t2); } else { return false; } } while (t2.getType() == TermType.LIST); return t2.unify(t1); }