用于在有向图中返回特定范围的节点的算法

时间:2010-04-17 05:27:15

标签: algorithm graph

我有一个包含两个列表类型的类Graph,即节点和边

我有一个功能

List<int> GetNodesInRange(Graph graph, int Range)

当我得到这些参数时,我需要一个算法,该算法将通过图形并返回节点列表,仅作为范围的深度(级别)。 该算法应该能够容纳大量节点和大范围。

在此之上,我应该使用类似的功能

List<int> GetNodesInRange(Graph graph, int Range, int selected)

我希望能够从中向外搜索指定的向外(范围)节点数。

alt text http://www.freeimagehosting.net/uploads/b110ccba58.png

所以在第一个函数中,如果我传递节点并且需要一个2的范围,我希望结果返回蓝色框中显示的节点。

另一个函数,如果我在图中传递节点,范围为1并且从节点5开始,我希望它返回满足此条件的节点列表(放在橙色框中)

3 个答案:

答案 0 :(得分:2)

您需要的只是一个深度限制breadth-first searchdepth-first search,可以选择忽略边缘方向性。


这是一个可以帮助您的递归定义:

  • 我是我自己唯一的第一名。
  • 我知道我的近邻是谁。
  • 如果是N > 1,那么我自己的范围N就是N-1
    • 所有来自我的邻居的{{1}}范围的联合

答案 1 :(得分:0)

它应该是一个递归函数,找到所选邻居,然后找到每个邻居的邻居,直到范围为0. DFS搜索类似的东西:

List<int> GetNodesInRange(Graph graph, int Range, int selected){
  var result = new List<int>();
  result.Add( selected );
  if (Range > 0){
    foreach ( int neighbour in GetNeighbours( graph, selected ) ){
      result.AddRange( GetNodesInRange(graph, Range-1, neighbour) );
    }
  }
  return result;
}

如果可能,您还应检查周期。此代码用于树结构。

答案 2 :(得分:0)

// get all the nodes that are within Range distance of the root node of graph
Set<int> GetNodesInRange(Graph graph, int Range)
{
    Set<int> out = new Set<int>();
    GetNodesInRange(graph.root, int Range, out);
    return out;
}

// get all the nodes that are within Range successor distance of node
// accepted nodes are placed in out
void GetNodesInRange(Node node, int Range, Set<int> out)
{
    boolean alreadyVisited = out.add(node.value);
    if (alreadyVisited) return;
    if (Range == 0) return;
    // for each successor node
    {
        GetNodesInRange(successor, Range-1, out);
    }
}


// get all the nodes that are within Range distance of selected node in graph
Set<int> GetNodesInRange(Graph graph, int Range, int selected)
{
    Set<int> out = new Set<int>();
    GetNodesInRange(graph, Range, selected, out);
    return out;
}

// get all the nodes that are successors of node and within Range distance
//     of selected node
// accepted nodes are placed in out
// returns distance to selected node
int GetNodesInRange(Node node, int Range, int selected, Set<int> out)
{
    if (node.value == selected)
    {
        GetNodesInRange(node, Range-1, out);
        return 1;
    }
    else
    {
        int shortestDistance = Range + 1;
        // for each successor node
        {
            int distance = GetNodesInRange(successor, Range, selected, out);
            if (distance < shortestDistance) shortestDistance = distance;
        }
        if (shortestDistance <= Range)
        {
            out.add(node.value);
        }
        return shortestDistance + 1;
    }
}

我稍微修改了您的要求,以返回Set而不是List

GetNodesInRange(Graph, int, int)方法不会处理包含循环的图形。这可以通过维护已经访问过的节点集合来克服。 GetNodesInRange(Graph, int)方法利用了out集合是受访节点的集合来克服周期的事实。

注意:这已经 以任何方式进行了测试。