使用Z3进行线性算术查询的性能问题

使用Z3进行线性算术查询的性能问题,z3,Z3,我正在写一个静态分析工具,需要执行一些查询到oracle解决线性整数算术问题。在我的第一个版本中,我在OCaml中实现了一个Presburger算法的决策过程(为了好玩和赚钱)。在大型项目中,我的决策过程成为瓶颈,因此我决定转到Z3 我的第一个结果令人失望,所以我认为我对Z3API做了一些错误的事情。我观察到,在简单的程序中,Z3的分析速度比我天真的自制实现慢100多倍。经过一些琐碎的基准测试,我认为罪魁祸首是: let unsat ps = let open Z3.Solver in

我正在写一个静态分析工具,需要执行一些查询到oracle解决线性整数算术问题。在我的第一个版本中,我在OCaml中实现了一个Presburger算法的决策过程(为了好玩和赚钱)。在大型项目中,我的决策过程成为瓶颈,因此我决定转到Z3

我的第一个结果令人失望,所以我认为我对Z3API做了一些错误的事情。我观察到,在简单的程序中,Z3的分析速度比我天真的自制实现慢100多倍。经过一些琐碎的基准测试,我认为罪魁祸首是:

let unsat ps =
  let open Z3.Solver in
  let solver = mk_solver ctx None in
  add solver [ps];
  check solver [] <> SATISFIABLE
让unsat-ps=
让我们打开Z3.Solver
让解算器=mk_解算器ctx无输入
添加解算器[ps];
检查解算器[]是否可满足
我使用这个函数数百次(在大型程序中使用数千次)。编码在
ps
中的问题的形式是
(不是(暗示(和X X X)Y))
,其中连词通常少于10个连词,
X
Y
是简单的线性不等式。这些问题很容易解决,所以我认为我的性能问题更多地与脚手架代码有关


我的问题是,如何降低每次调用此
unsat
函数的成本?

创建一次解算器并在空状态下使用push/pop似乎可以稍微提高性能。但对我的申请来说还不够。