Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/asp.net/33.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
Java中的广度优先搜索_Java_Arraylist_Breadth First Search - Fatal编程技术网

Java中的广度优先搜索

Java中的广度优先搜索,java,arraylist,breadth-first-search,Java,Arraylist,Breadth First Search,我必须在Java中运行广度优先搜索以获得作业。我有一个5x5网格的瓷砖(总共24个-1个瓷砖为“空白”)。搜索的重点是通过向上、向下、向左或向右移动“空白”来重新排列磁贴,最终将磁贴重新排列为正确的顺序 为了进行此搜索,我创建了一个Arraylist“queue”。我有一个方法,它获取这个arraylist的索引0处的状态,找到每个可以跟随的合法移动,然后将它们分别添加到arraylist的末尾 理论上,这一过程一直持续到最终找到“目标状态”。问题是,当我运行搜索时,“队列”数组列表只会继续变得

我必须在Java中运行广度优先搜索以获得作业。我有一个5x5网格的瓷砖(总共24个-1个瓷砖为“空白”)。搜索的重点是通过向上、向下、向左或向右移动“空白”来重新排列磁贴,最终将磁贴重新排列为正确的顺序

为了进行此搜索,我创建了一个Arraylist“queue”。我有一个方法,它获取这个arraylist的索引0处的状态,找到每个可以跟随的合法移动,然后将它们分别添加到arraylist的末尾

理论上,这一过程一直持续到最终找到“目标状态”。问题是,当我运行搜索时,“队列”数组列表只会继续变得越来越大。今天我让它运行了几个小时,仍然没有找到解决方案

这表明我可能用了错误的方法来解决这个问题,有一种更好的方法可以用Java进行广度优先搜索。我知道我的解决方案确实有效(最终),因为当我使用与目标状态没有太大差异的开始状态时,找到正确的路径不会花费太长时间。然而,我已经得到了一个开始状态来使用,不幸的是,这离目标状态还差得远


任何提示或提示都将不胜感激

虽然这可能不在你的作业范围内,但有一种算法可以解决这类难题。基本上,除了最后两行外,每行都有两个动作,最后两行都有两个动作。使用这种方法可以获得更快的解决方案


不幸的是,由于这是一项任务,您无疑需要进行暴力搜索。

乍一看,您可能会在图形中出现重复的状态和循环。您可能需要研究一些方法来确定两个州是否相同,以及您是否曾经访问过一个州


编辑:抛开算法限制,也许有一个公式可以将Y位置的块X移动到Z位置,而不分发任何其他平铺。考虑到这一点,您可以计算所需的所有转换。我现在正在思考这个问题。

我已经完成了“暴力搜索”——问题是,对于5x5网格,有太多的组合,这需要永远的时间。我在上班的时候让它一直在运行…8小时后,它还在运行,队列数组列表大小达到了10万个不同的状态,我的电脑听起来好像要过热爆炸了,哈哈


我知道我的代码是有效的(最终,就像我说的),所以我很乐意提交它。我只是担心找到解决方案所需的时间,并想知道除了使用arraylist创建队列之外,是否还有更好的方法可以使用。

首先,我肯定会使用实际的队列对象而不是arraylist。这里是队列接口上的JavaAPI页面:-您可以在该页面上看到队列的许多实现者,如果您不知道选择什么,一个简单的LinkedList就可以了。ArrayList将对性能产生巨大的影响,因为它只是从末尾快速删除,如果从数组中的任何其他位置删除,它必须将所有内容向下移动一个(!)。您将在最后排队,在开始时退队,因此

现在,您没有明确提到在处理完项目后,您正在将其从队列中删除,所以我认为您是这样做的,因为这可能是一个原因


您是否必须特别使用广度优先搜索?如果我算对了,一共有25个!(阶乘)组合,也就是155112100433309885984000000个组合,理论上这意味着如果你做的是广度优先搜索,你的算法不可能完成。是否不允许深度优先搜索?如果您必须使用广度优先搜索,那么使搜索速度更快的唯一方法就是删除那些不可能导致最佳解决方案的状态。我不知道你会怎么做。

我认为这个练习的想法是让你意识到深度优先搜索是解决这个特殊难题的更好方法。

没有重复检查的广度优先搜索肯定会给你像你看到的那样的结果。事实上,证明您实现的算法永远不会终止是相当简单的。尽管如此,请随时等待……:-)

您需要的是一个辅助数据结构(最好是
集合
),用于存储预先检查的位置。因此,部分代码如下所示:

public Queue<Position> queue = new LinkedList<Position>();
public Set<Position> done = new HashSet<Position>();

public Position[] findPath(Position start, Position goal) {
    if (done.contains(start)) return null;

    done.add(start);
    // add subsequent states to `queue`
    ...
}
publicqueue=newlinkedlist();
public Set done=new HashSet();
公共职位[]findPath(职位开始、职位目标){
if(done.contains(start))返回null;
完成。添加(开始);
//将后续状态添加到“队列”`
...
}

如其他答案所述,在这种情况下,深度优先搜索是一个更好的解决方案。假设
目标
位置是可到达的,除了最人为的位置外,它应该为所有位置产生指数级的优越搜索时间。

我必须实际为这两个位置编写代码。因此,我将进入深度优先搜索。在我这么做之前,我只是想确保我不会因为编写花了一天时间才找到解决方案的代码而被嘲笑

你没有说你是否检查了这个,但听起来你不是在修剪周期

首先,假设代替表示移动某个方向上的空白方块,而是提供被移动的瓦片编号。(它保证是唯一的)现在假设一个合法的移动是“3”-将tile#3移动到空空间中。结果是一个新的电路板布局。合法的做法是再次移动tile 3,现在您又回到了起点

滑块拼图可以很容易地有更大的周期。如果有一个2x2的网格,其中有1-2-3-empty,那么
State 1: ABCDEFGHIJKLMNOP
State 2: BCADEFGHIJKLMNOP