z3的可扩展性

z3的可扩展性,z3,z3py,Z3,Z3py,我想提高SMT解决方案的可扩展性。我实际上已经实现了增量求解。但我想提高更多。在不了解问题本身的情况下,还有其他通用的方法来改进它吗?没有一种“技巧”可以使z3更好地适用于任意问题。这实际上取决于实际问题是什么,以及你有什么样的约束。当然,这适用于任何一般计算问题,但它确实适用于SMT求解器的上下文 话虽如此,根据我的经验,以下是一些大致按易用性顺序排列的一般想法: 阅读编程Z3一书这是一篇非常好的文章,它将教你很多关于Z3的架构以及最好的习惯用法。您可能会遇到一些直接适用于您的问题的问题: 将

我想提高SMT解决方案的可扩展性。我实际上已经实现了增量求解。但我想提高更多。在不了解问题本身的情况下,还有其他通用的方法来改进它吗?

没有一种“技巧”可以使z3更好地适用于任意问题。这实际上取决于实际问题是什么,以及你有什么样的约束。当然,这适用于任何一般计算问题,但它确实适用于SMT求解器的上下文

话虽如此,根据我的经验,以下是一些大致按易用性顺序排列的一般想法:

阅读
编程Z3
一书
这是一篇非常好的文章,它将教你很多关于Z3的架构以及最好的习惯用法。您可能会遇到一些直接适用于您的问题的问题:

将布尔值保持为布尔值而不是整数切勿使用整数表示布尔值。(也就是说,使用
1
表示真,使用
0
表示假;使用乘法表示
等。这是一个可怕的想法,会扼杀下面强大的SAT引擎。)必要时显式转换。人们倾向于使用这些技巧的大多数问题都涉及到计算有多少布尔值为真等等:这些问题应该使用内置于解算器中的伪布尔策略来解决。(查找
pbEq
pbLt
等)

除非绝对必要,否则不要进行优化优化引擎不是增量的,也不是优化良好的(双关语)。与所有其他引擎相比,它的工作速度相当慢,这是有充分理由的:优化模理论是一件非常棘手的事情。除非你真的有一个优化问题要解决,否则就避免它。您还可以尝试优化“外部”解算器:进行
SAT
调用,获取结果,然后进行后续调用,要求“更小”的成本值。使用此技巧可能无法达到最佳效果,但经过几次迭代后,这些值可能已经足够好了。当然,结果如何完全取决于你的问题

案例拆分尝试通过对关键变量进行案例拆分来减少约束。示例:如果您处理的是浮点约束,比如;分别对法线、非法线、无穷大和NaN值进行案例拆分。根据您的特定领域,您可能有这样的语义类别,其中底层算法采用不同的路径,并且混合和匹配它们总是会给解算器带来困难。基于上下文的案例拆分可以加快速度

使用更快的机器和更多的内存这是不言而喻的;但是拥有足够的内存确实会加速某些问题,特别是当你有很多变量的时候。得到最大的机器,你可以

利用您的核心您可能有一台包含许多核心的机器,而且您的操作系统很可能提供细粒度的多任务处理。利用这一点:启动z3的多个实例处理同一个问题,但使用不同的策略、随机种子等。;然后取第一个完成的结果。如果您有一个巨大的约束集,那么随机种子可以发挥重要作用,因此运行更多具有不同种子值的实例可以让您平均“幸运”

尝试使用并行求解大多数SAT/SMT求解器算法本质上是顺序的。已经有很多关于如何并行化某些算法的论文,但大多数引擎都没有并行的对应项。z3有一个用于并行求解的接口,尽管它的宣传较少,而且相当挑剔。试一试,看看是否有帮助。详情如下:

ProfileProfile z3源代码本身在您的问题上运行,请参阅 热点在哪里。看看是否可以向开发人员推荐代码改进来解决这些问题。(更好的是,提交一个pull请求!)不用说,这将需要对z3本身进行深入研究,可能不适合最终用户

底线:没有免费午餐。没有一种方法可以使z3更好地解决您的问题。但上述想法可能有助于提高运行时间。如果您详细描述了您正在处理的特定问题,您很可能会得到更好的建议,因为它适用于您的约束