【问题标题】:Backtracking search for constraint satisfaction problem implementation回溯搜索约束满足问题实现
【发布时间】:2018-11-08 03:51:49
【问题描述】:

对于家庭作业,我的目标是使用最小剩余值、程度启发式和前向检查进行回溯搜索。需要解决一个布尔可满足性问题,该问题由 3 个布尔变量的集合组成,或者相互关联,并且每个集合必须评估为真。就我目前的实现而言,我相信它最终会解决它,但是完成它需要很长时间,以至于我最终遇到了 java 堆内存不足错误。

除此之外,我的实现如下:

  • 每个约束都有一个数组列表
  • 一个值数组,索引是每个变量的值,这些变量要么是真、要么是假,或者尚未给定值,最初都没有给定值。第 0 个元素用作标志。
  • 每个变量的域的数组:真或假,只有真,只有假或没有可能的值,初始为真或假
  • 数组的arrayList,每个数组是一个值列表;习惯于避免两次尝试相同的事情
  • 变量处于约束中的次数的数组:这是启发式度数

向后搜索返回一个值数组,并接受一个值数组和一个域数组

首先检查列表中的每个约束,以确保每个变量的域都可以使其正确。如果它们都不起作用,则设置第 0 个标志并退出。此外,如果 2 个变量的域使得第三个变量必须为真才能使语句起作用,则更改该变量的域。

在它通过该步骤后,它会检查 vals 数组中的每个变量是否都有赋值,从而成功结束程序。

接下来,它创建一个临时数组来跟踪它尝试过的值,并开始一个循环。在内部,它添加每个具有找到的最小域(MRV)的域并且没有值/尚未尝试的变量,将其添加到列表中,如果找不到则退出递归。然后,它根据启发式度数数组从变量中选择出现最多的变量。在平局上,它选择出现在平局中的最后一个,并设置一个标志,这样我们就不会在同一个递归中再次尝试该变量。

仍然在循环内部,它首先尝试将域和该变量的值设置为 true,如果域不仅为 false,则为 false,否则为 false。它检查变量的值组合之前是否已经完成,如果有,则重新选择。如果没有,它会将该值组合添加到列表中并执行递归步骤。如果该递归步骤返回一个停止标志,则将值交换回它们对于域和所选变量的值的值,然后再次尝试,这次将域和值设为 false,但首先它将其添加到尝试组合的列表中,重新选择它是否已经存在,并重置所有还没有值的变量的域,然后执行递归步骤。如果同样失败,则重置变量选择域和值的值,并尝试在同一循环中选择不同的变量。一旦完成或所有组合都失败,循环就会中断,然后返回值数组。

我可以说它不会重复,但我不知道如何修复/加速我的实现,以便它在合理的时间运行。

【问题讨论】:

  • 可能会检查一些开源 CSP 求解器的实现。 python有一些开源实现-例如

标签: java algorithm artificial-intelligence


【解决方案1】:

第一步是为领域创建知识模型。这可以使用领域特定语言 (DSL) 来完成。在 DSL 语法中,制定了该问题的可能解决方案。特定领域语言的期望副作用是,必须创建一个可以解析该语言的语法。这种语法可以以相反的顺序使用,称为“生成语法”。其目的是在 DSL 中包含尽可能多的领域知识,从而使求解器更容易测试所有状态。

不幸的是,该问题仅包含有关域本身的一些信息。根据描述,可以打开或关闭三个变量。这将生成一个可能的 2x2x2=8 状态空间,这对于域来说似乎有点太容易了,因为如果他测试了所有 8 个状态,求解器就完成了。所以我猜,这个问题有点难,但在描述中没有解释。然而,第一步是将问题转换为可以被语法解析的语言。

【讨论】:

    猜你喜欢
    • 2019-06-03
    • 2012-05-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-04-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多