예제 #1
0
def formulaDistributeDisjunctions(f):
    """
    Convert a Skolemized formula in prefix-NNF form into Conjunctive
    Normal Form.
    """
    arg1 = None
    arg2 = None
    if f.isQuantified():
        arg1 = f.child1
        arg2 = formulaDistributeDisjunctions(f.child2)
        f = Formula(f.op, arg1, arg2)
    elif f.isLiteral():
        pass
    else:
        if f.hasSubform1():
            arg1 = formulaDistributeDisjunctions(f.child1)
        if f.hasSubform2():
            arg2 = formulaDistributeDisjunctions(f.child2)
        f = Formula(f.op, arg1, arg2)
    if f.op == "|":
        if f.child1.op == "&":
            # (P&Q)|R -> (P|R) & (Q|R)
            arg1 = Formula("|", f.child1.child1, f.child2)
            arg2 = Formula("|", f.child1.child2, f.child2)
            f = Formula("&", arg1, arg2)
            f = formulaDistributeDisjunctions(f)
        elif f.child2.op == "&":
            # (R|(P&Q) -> (R|P) & (R|Q)
            arg1 = Formula("|", f.child1, f.child2.child1)
            arg2 = Formula("|", f.child1, f.child2.child2)
            f = Formula("&", arg1, arg2)
            f = formulaDistributeDisjunctions(f)
    return f
예제 #2
0
def formulaNNF(f, polarity):
    """
    Convert f into a NNF. Equivalences (<=>) are eliminated
    polarity-dependend, top to bottom. Returns (f', m), where f' is a
    NNF of f, and m indicates if f!=f'
    """

    normalform = False
    modified = False

    while not normalform:
        normalform = True
        f, m = rootFormulaNNF(f, polarity)
        modified |= m

        if f.op == "~":
            handle, m = formulaNNF(f.child1, -polarity)
            if m:
                normalform = False
                f = Formula("~", handle)
        elif f.op in ["!", "?"]:
            handle, m = formulaNNF(f.child2, polarity)
            if m:
                normalform = False
                f = Formula(f.op, f.child1, handle)
        elif f.op in ["|", "&"]:
            handle1, m1 = formulaNNF(f.child1, polarity)
            handle2, m2 = formulaNNF(f.child2, polarity)
            m = m1 or m2
            if m:
                normalform = False
                f = Formula(f.op, handle1, handle2)
        else:
            assert f.isLiteral()
        modified |= m

    return f, modified