Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/jquery/84.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Z3和DIMACS输出_Z3 - Fatal编程技术网

Z3和DIMACS输出

Z3和DIMACS输出,z3,Z3,Z3目前支持输入的DIMACS格式。在解决问题之前,是否有任何方法输出问题的DIMACS格式?我的意思是将问题转换为系统CNFs并以DIMACS格式输出。 如果没有,任何朝这个方向发展的想法都会非常有用。DIMACS格式非常原始,它只支持布尔变量。Z3并没有将每个问题都简化为SAT。有些问题是使用命题SAT解算器解决的,但这不是规则。这通常仅在输入仅包含布尔和/或位向量变量时发生。此外,即使输入问题只包含布尔和位向量变量,也不能保证Z3将使用纯SAT解算器来解决它 也就是说,您可以使用来控制Z3

Z3目前支持输入的DIMACS格式。在解决问题之前,是否有任何方法输出问题的DIMACS格式?我的意思是将问题转换为系统CNFs并以DIMACS格式输出。
如果没有,任何朝这个方向发展的想法都会非常有用。

DIMACS格式非常原始,它只支持布尔变量。Z3并没有将每个问题都简化为SAT。有些问题是使用命题SAT解算器解决的,但这不是规则。这通常仅在输入仅包含布尔和/或位向量变量时发生。此外,即使输入问题只包含布尔和位向量变量,也不能保证Z3将使用纯SAT解算器来解决它

也就是说,您可以使用来控制Z3。例如,对于位向量问题,以下策略将其转换为CNF格式的命题公式。将其转换为DIMAC应该很简单。这是一个例子。您可以在以下网站在线试用:

x,y,z=BitVecs('x y z',16)
g=目标()
g、 加(x==y,z>If(x<0,x,-x))
打印g
#t是一种将位向量问题简化为命题CNF的策略
t=Then('simplify'、'bit blast'、'tseitin cnf')
子目标=t(g)
断言len(子目标)=1
#遍历第一个子目标的每个子句
对于子目标[0]中的c:
打印c

多亏了莱昂纳多的回答,我想出了这个代码,可以满足你的需求:

private static void Output(Context ctx,Solver slv)
{
    var goal = ctx.MkGoal();
    goal.Add(slv.Assertions);
    var applyResult = ctx.Then(ctx.MkTactic("simplify"),
        ctx.MkTactic("bit-blast"),
        ctx.MkTactic("tseitin-cnf")).Apply(goal);

    Debug.Assert(applyResult.Subgoals.Length==1);

    var map = new Dictionary<BoolExpr,int>();
    foreach (var f in applyResult.Subgoals[0].Formulas)
    {
        Debug.Assert(f.IsOr);
        foreach (var e in f.Args)
            if (e.IsNot)
            {
                Debug.Assert(e.Args.Length==1);
                Debug.Assert(e.Args[0].IsConst);
                map[(BoolExpr)e.Args[0]] = 0;
            }
            else
            {
                Debug.Assert(e.IsConst);
                map[(BoolExpr)e] = 0;
            }
    }

    var id = 1;
    foreach (var key in map.Keys.ToArray())
        map[key] = id++;

    using (var fos = File.CreateText("problem.cnf"))
    {
        fos.WriteLine("c DIMACS file format");
        fos.WriteLine($"p cnf {map.Count} {applyResult.Subgoals[0].Formulas.Length}");
        foreach(var f in applyResult.Subgoals[0].Formulas)
        {
            foreach (var e in f.Args)
                if (e.IsNot)
                    fos.Write($"{map[(BoolExpr)e.Args[0]]} ");
                else
                    fos.Write($"-{map[(BoolExpr)e]} ");

            fos.WriteLine("0");
        }
    }
}
私有静态无效输出(上下文ctx、解算器slv)
{
var goal=ctx.MkGoal();
添加(slv.Assertions);
var applyResult=ctx.Then(ctx.mk)(“简化”),
ctx.mktractic(“钻头爆炸”),
ctx.mktractic(“tseitin cnf”)。应用(目标);
Assert(applyResult.Subgoals.Length==1);
var map=newdictionary();
foreach(applyResult.Subgoals[0].公式中的var f)
{
断言(f.IsOr);
foreach(f.Args中的变量e)
如果(e.IsNot)
{
Assert(e.Args.Length==1);
Assert(e.Args[0].IsConst);
map[(BoolExpr)e.Args[0]]=0;
}
其他的
{
Assert(e.IsConst);
map[(BoolExpr)e]=0;
}
}
var-id=1;
foreach(map.Keys.ToArray()中的var key)
map[key]=id++;
使用(var fos=File.CreateText(“problem.cnf”))
{
fos.WriteLine(“c DIMACS文件格式”);
fos.WriteLine($“p cnf{map.Count}{applyResult.Subgoals[0].Formulas.Length}”);
foreach(applyResult.Subgoals[0].公式中的var f)
{
foreach(f.Args中的变量e)
如果(e.IsNot)
fos.Write($“{map[(BoolExpr)e.Args[0]}”);
其他的
fos.Write($“-{map[(BoolExpr)e]}”);
fos.WriteLine(“0”);
}
}
}
要使其工作,您应该通过调用
slv.Assert(…)
将所有约束直接添加到解算器中

private static void Output(Context ctx,Solver slv)
{
    var goal = ctx.MkGoal();
    goal.Add(slv.Assertions);
    var applyResult = ctx.Then(ctx.MkTactic("simplify"),
        ctx.MkTactic("bit-blast"),
        ctx.MkTactic("tseitin-cnf")).Apply(goal);

    Debug.Assert(applyResult.Subgoals.Length==1);

    var map = new Dictionary<BoolExpr,int>();
    foreach (var f in applyResult.Subgoals[0].Formulas)
    {
        Debug.Assert(f.IsOr);
        foreach (var e in f.Args)
            if (e.IsNot)
            {
                Debug.Assert(e.Args.Length==1);
                Debug.Assert(e.Args[0].IsConst);
                map[(BoolExpr)e.Args[0]] = 0;
            }
            else
            {
                Debug.Assert(e.IsConst);
                map[(BoolExpr)e] = 0;
            }
    }

    var id = 1;
    foreach (var key in map.Keys.ToArray())
        map[key] = id++;

    using (var fos = File.CreateText("problem.cnf"))
    {
        fos.WriteLine("c DIMACS file format");
        fos.WriteLine($"p cnf {map.Count} {applyResult.Subgoals[0].Formulas.Length}");
        foreach(var f in applyResult.Subgoals[0].Formulas)
        {
            foreach (var e in f.Args)
                if (e.IsNot)
                    fos.Write($"{map[(BoolExpr)e.Args[0]]} ");
                else
                    fos.Write($"-{map[(BoolExpr)e]} ");

            fos.WriteLine("0");
        }
    }
}