Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/string/5.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
Graph 使用集合而不是队列进行宽度优先搜索_Graph_Breadth First Search - Fatal编程技术网

Graph 使用集合而不是队列进行宽度优先搜索

Graph 使用集合而不是队列进行宽度优先搜索,graph,breadth-first-search,Graph,Breadth First Search,我正在使用BFS查找连接的组件。我决定使用一个集合来跟踪访问的节点来实现它。这种方法的问题是一个顶点可能会被添加到队列中两次。所以我把队列改成了set。我不关心访问顺序,所有节点访问一次,算法运行良好。当然,这不再是经典的BFS:顺序被打破了 伪代码: Set visited; Set to_visit; visited.insert(start) to_visit.insert(start) while (to_visit is not empty){ current = to_vi

我正在使用BFS查找连接的组件。我决定使用一个集合来跟踪访问的节点来实现它。这种方法的问题是一个顶点可能会被添加到队列中两次。所以我把队列改成了set。我不关心访问顺序,所有节点访问一次,算法运行良好。当然,这不再是经典的BFS:顺序被打破了

伪代码:

Set visited;
Set to_visit; 
visited.insert(start)
to_visit.insert(start)
while (to_visit is not empty){
    current = to_visit.first
    to_visit.delete(current)
    for each neighbour of current {
        isNew = visited.insert(neighbour)
        if (isNew) {
            to_visit.insert(neighbour)
        }
    }
}
queue= []
set = [0,0,0,0,0....,0]
queue.push(firstVertex)

while(!queue.isEmpty())
{
     vertex curr = queue.pop()

     if(set[curr] == 1) //already visited
     {
          continue;
     }
     set[curr] = 1;
     foreach(child of curr)
     {
          queue.push(child);
     }
}

我很确定我不是第一个“发明”它的人。我想知道:这个“我不在乎”的搜索怎么叫

如何将其添加到队列中两次?您必须确保队列中的元素是唯一的,若顶点是对象,请添加标志“visited=false”,当您尝试将顶点添加到队列中时,请首先检查标志,仅当其为false时才继续,然后将其更改为true

如果顶点只是一个数字,那么创建一个表示每个顶点标志的布尔数组

伪代码:

Set visited;
Set to_visit; 
visited.insert(start)
to_visit.insert(start)
while (to_visit is not empty){
    current = to_visit.first
    to_visit.delete(current)
    for each neighbour of current {
        isNew = visited.insert(neighbour)
        if (isNew) {
            to_visit.insert(neighbour)
        }
    }
}
queue= []
set = [0,0,0,0,0....,0]
queue.push(firstVertex)

while(!queue.isEmpty())
{
     vertex curr = queue.pop()

     if(set[curr] == 1) //already visited
     {
          continue;
     }
     set[curr] = 1;
     foreach(child of curr)
     {
          queue.push(child);
     }
}

您还可以将标志从true/false更改为组件编号

谢谢,我知道BFS的正确实施。实际上我也在做同样的事情,但是通过集合保持队列的唯一性。在我的实现中,顶点在实际访问时被访问,而不是添加到队列中时。是的,使用set它也应该工作,只需将isVisited更改为mySet[vertex]=1或其他什么?但顺序还是一样的。我明白你的问题了!您可以在Begging上添加if语句,并检查curr是否已被访问。我将伪代码改为您的想法。
if(set[curr]==1)
篡改了算法的复杂性。一个顶点可以被多次考虑。使用一个集合来标记添加到队列中的顶点,使用一个集合来实际访问顶点。。。。。这正是我所做的!但是队列本身是无用的,因为我可以从集合中获取节点进行访问。