def helper(f, used, substs): if is_variable(f): if f in substs: return substs[f] else: return f if is_quantified(f): # does this quantifier use a variable that is already used? clashing = (used & set(f.vars)) # set intersection if len(clashing) > 0: for var in clashing: existing = used.union(*list(map(vars, substs.values()))) # rename any clashing variable var2 = variant(var, existing) substs[var] = var2 used.update(f.vars) arg = helper(f.args[0], used, substs) return Quantifier(f.op, [subst(substs, x) for x in f.vars], *[subst(substs, x) for x in f.args]) else: used.update(f.vars) arg = helper(f.args[0], used, substs) return Quantifier(f.op, f.vars, arg) else: return Expr(f.op, *[helper(x, used, substs) for x in f.args])
def formula_to_rst(f): """ Convert a FOL formula to an RST tree. """ get_log().debug(str(f)) if f.op == OP_AND: msgs = [formula_to_rst(x) for x in f.args] m = Message("Conjunction", None, *msgs) # test = lambda x: (x.op == '&' or x.op == '|') # if any(map(test, f.args)): # m.marker = ', and' # else: m.marker = "and" return m if f.op == OP_OR: msgs = [formula_to_rst(x) for x in f.args] m = Message("Disjunction", None, *msgs) # test = lambda x: (x.op != 'forall' and # x.op != 'exists') # if any(map(test, f.args)): # m.marker = ', or' # else: m.marker = "or" return m if f.op == OP_IMPLIES: msgs = [formula_to_rst(x) for x in f.args] m = Message("Imply", msgs[0], msgs[1]) return m if f.op == OP_IMPLIED_BY: msgs = [formula_to_rst(x) for x in f.args] m = Message("Imply", msgs[1], msgs[0]) return m if f.op == OP_EQUIVALENT: msgs = [formula_to_rst(x) for x in f.args] m = Message("Equivalent", msgs[0], msgs[1]) return m if f.op == OP_EQUALS: msgs = [formula_to_rst(x) for x in f.args] m = Message("Equality", msgs[0], *msgs[1:]) return m if f.op == OP_NOTEQUALS: msgs = [formula_to_rst(x) for x in f.args] m = Message("Inequality", msgs[0], *msgs[1:]) return m if f.op == OP_FORALL: vars = [formula_to_rst(x) for x in f.vars] msgs = [formula_to_rst(x) for x in f.args] m = Message("Quantifier", vars, *msgs) m.marker = "for all" return m if f.op == OP_EXISTS: vars = [formula_to_rst(x) for x in f.vars] msgs = [formula_to_rst(x) for x in f.args] m = Message("Quantifier", vars, *msgs) if len(f.vars) == 1: m.marker = "there exists" else: m.marker = "there exist" return m if f.op == OP_NOT and is_predicate(f.args[0]): get_log().debug("negated predicate: " + str(f)) arg = f.args[0] m = PredicateMsg(arg, *[formula_to_rst(x) for x in arg.args]) m._features = {"NEGATED": "true"} return m if f.op == OP_NOT and is_variable(f.args[0]): get_log().debug("negated variable: " + str(f)) arg = f.args[0] m = NounPhrase(PlaceHolder(arg.op), Word("not", "DETERMINER")) return m if f.op == OP_NOT: get_log().debug("negated formula: " + str(f)) msgs = [formula_to_rst(x) for x in f.args] m = Message("Negation", msgs[0], *msgs[1:]) m.marker = "it is not the case that" return m if is_predicate(f): get_log().debug("predicate: " + str(f)) return PredicateMsg(f, *[formula_to_rst(x) for x in f.args]) if is_function(f): get_log().debug("function: " + str(f)) return PlaceHolder(f.op, PredicateMsg(f, *[formula_to_rst(x) for x in f.args])) else: get_log().debug("None: " + repr(f)) return PredicateMsg(f)