pythonmathsatboolean-algebracnf

CNF by truth table


I have a boolean function that is presented by truth table.

In total it is 10 variables and I'd like to get CNF with a reasonable length (not necessary the shortest, but short enough).

How can I do it?

Python script or any public available software such as Mathematica/Mapple/etc will work fine for me as well.


Solution

  • The sympy package allows you to do this out-of-the box. (https://www.sympy.org/en/index.html)

    Here's a simple example. Assuming you've three variables and the truth table encodes the following set:

      (x & y & !z) \/ (x & !y & z)
    

    (i.e., only the rows corresponding to x=true, y=true, z=false and x=true, y=false, z=true are true, while all others are false). You can easily code this and convert to CNF as follows:

    $ python3
    Python 3.8.5 (default, Jul 21 2020, 10:48:26)
    [Clang 11.0.3 (clang-1103.0.32.62)] on darwin
    Type "help", "copyright", "credits" or "license" for more information.
    >>> from sympy import *
    >>> x, y, z = symbols('x y z')
    >>> simplify_logic((x & y & ~z) | (x & ~y & z), form="cnf")
    x & (y | z) & (~y | ~z)
    

    simplify_logic can convert to CNF or DNF, based on the form argument. See here: https://github.com/sympy/sympy/blob/c3087c883be02ad228820ff714ad6eb9af1ad868/sympy/logic/boolalg.py#L2746-L2827

    Note that CNF expansion can be costly in general, and Tseitin encoding is the preferred method to avoid this complexity (https://en.wikipedia.org/wiki/Tseytin_transformation). But it has the disadvantage of introducing new variables.