简体   繁体   English

QuickGraph - 是否有算法用于查找一组顶点的所有父项(直到根顶点)

[英]QuickGraph - is there algorithm for find all parents (up to root vertex's) of a set of vertex's

In QuickGraph - is there algorithm for find all parents (up to root vertex's) of a set of vertex's. 在QuickGraph中 - 是否有算法用于查找一组顶点的所有父项(直到根顶点)。 In other words all vertex's which have somewhere under them (on the way to the leaf nodes) one or more of the vertexs input. 换句话说,所有顶点都位于它们下面(在去往叶节点的路上)一个或多个顶点输入。 So if the vertexs were Nodes, and the edges were a depends on relationship, find all nodes that would be impacted by a given set of nodes. 因此,如果顶点是节点,并且边缘取决于关系,则查找将受给定节点集影响的所有节点。

If not how hard is it to write one's own algorithms? 如果没有写出自己的算法有多难?

I used Doug's answer and found out that if there are more than one parent for a vertex, his solution only provides one of the parents. 我使用Doug的答案,发现如果顶点有多个父级,他的解决方案只提供一个父级。 I am not sure why. 我不知道为什么。

So, I created my own version which is as follows: 所以,我创建了自己的版本,如下所示:

    public IEnumerable<T> GetParents(T vertexToFind)
    {
        IEnumerable<T> parents = null;

        if (this.graph.Edges != null)
        {
            parents = this.graph
                .Edges
                .Where(x => x.Target.Equals(vertexToFind))
                .Select(x => x.Source);
        }

        return parents;
    }

Here's what I've used to accomplish a predecessor search on a given vertex: 这是我用来完成给定顶点上的前任搜索:

IBidirectionalGraph<int, IEdge<int>> CreateGraph(int vertexCount)
{
    BidirectionalGraph<int, IEdge<int>> graph = new BidirectionalGraph<int, IEdge<int>>(true);
    for (int i = 0; i < vertexCount; i++)
        graph.AddVertex(i);

    for (int i = 1; i < vertexCount; i++)
        graph.AddEdge(new Edge<int>(i - 1, i));

    return graph;
}

static public void Main()
{
    IBidirectionalGraph<int, IEdge<int>> graph = CreateGraph(5);

    var dfs = new DepthFirstSearchAlgorithm<int, IEdge<int>>(graph);            
    var observer = new VertexPredecessorRecorderObserver<int, IEdge<int>>();

    using (observer.Attach(dfs)) // attach, detach to dfs events
        dfs.Compute();

    int vertexToFind = 3;
    IEnumerable<IEdge<int>> edges;
    if (observer.TryGetPath(vertexToFind, out edges))
    {
        Console.WriteLine("To get to vertex '" + vertexToFind + "', take the following edges:");
        foreach (IEdge<int> edge in edges)
            Console.WriteLine(edge.Source + " -> " + edge.Target);
    }
}

Note that if you know your root beforehand, you can specify it in the dfs.Compute() method (ie dfs.Compute(0) ). 请注意,如果您事先知道根,则可以在dfs.Compute()方法中指定它(即dfs.Compute(0) )。

-Doug -Doug

You either need to maintain a reversed graph, or create a wrapper over the graph that reverses every edge. 您需要维护反转图形,或者在图形上创建一个反转每个边缘的包装器。 QuickGraph has the ReversedBidirectionalGraph class that is a wrapper intended just for that, but it does not seem to work with the algorithm classes because of generic type incompatibility. QuickGraph有ReversedBidirectionalGraph类,它是一个专门用于它的包装器,但由于泛型类型不兼容,它似乎不适用于算法类。 I had to create my own wrapper class: 我必须创建自己的包装类:

class ReversedBidirectionalGraphWrapper<TVertex, TEdge> : IVertexListGraph<TVertex, TEdge> where TEdge : IEdge<TVertex> 
{
  private BidirectionalGraph<TVertex, TEdge> _originalGraph;
  public IEnumerable<TEdge> OutEdges(TVertex v)
    {
        foreach (var e in _graph.InEdges(v))
        {
            yield return (TEdge)Convert.ChangeType(new Edge<TVertex>(e.Target, e.Source), typeof(TEdge));
        }
    } //...implement the rest of the interface members using the same trick
}

Then run DFS or BFS on this wrapper: 然后在此包装器上运行DFS或BFS:

var w = new ReversedBidirectionalGraphWrapper<int, Edge<int>>(graph);    
var result = new List<int>();    
var alg = new DepthFirstSearchAlgorithm<int, Edge<int>>(w);
alg.TreeEdge += e => result.Add(e.Target);    
alg.Compute(node);

Doug's answer is not correct, because DFS will only visit the downstream subgraph. 道格的答案是不正确的,因为DFS只会访问下游子图。 The predecessor observer does not help. 前任观察员没有帮助。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM