Esempio n. 1
0
        /// <summary>
        /// Traverses graph from start vertex.
        /// </summary>
        /// <param name="graph">Graph instance.</param>
        /// <param name="startVertex">Vertex that search starts from.</param>
        /// <param name="action">Action that needs to be executed on each graph vertex.</param>
        /// <param name="visited">Hash set with visited vertices.</param>
        private void Bfs(IDirectedWeightedGraph <T> graph, Vertex <T> startVertex, Action <Vertex <T> >?action, HashSet <Vertex <T> > visited)
        {
            var queue = new Queue <Vertex <T> >();

            queue.Enqueue(startVertex);

            while (queue.Count > 0)
            {
                var currentVertex = queue.Dequeue();

                if (currentVertex == null || visited.Contains(currentVertex))
                {
                    continue;
                }

                foreach (var vertex in graph.GetNeighbors(currentVertex))
                {
                    queue.Enqueue(vertex !);
                }

                action?.Invoke(currentVertex);

                visited.Add(currentVertex);
            }
        }
Esempio n. 2
0
        /// <summary>
        /// Traverses graph from start vertex.
        /// </summary>
        /// <param name="graph">Graph instance.</param>
        /// <param name="startVertex">Vertex that search starts from.</param>
        /// <param name="action">Action that needs to be executed on each graph vertex.</param>
        /// <param name="visited">Hash set with visited vertices.</param>
        private void Dfs(IDirectedWeightedGraph <T> graph, Vertex <T> startVertex, Action <Vertex <T> >?action, HashSet <Vertex <T> > visited)
        {
            action?.Invoke(startVertex);

            visited.Add(startVertex);

            foreach (var vertex in graph.GetNeighbors(startVertex))
            {
                if (vertex == null || visited.Contains(vertex))
                {
                    continue;
                }

                Dfs(graph, vertex !, action, visited);
            }
        }
Esempio n. 3
0
        // X - set of explored vertices of graph G
        // V-X - set of unexplored vertices of graph G
        //
        // Invariant.
        //     The key of a vertex w belongs to V-X is the min Dijkstra score of an edge with tail v belongs to X
        //     and head w, or +infinity if no such edge exists.
        //     key(w) = min len(v) + l(vw)
        //
        // DijkstraSearch(graph G, vertex s):
        //     // Initialization
        //     X = empty set
        //     H = empty min heap
        //     key(s) = 0
        //     for each vertex V in G.vertices do: key(V) = +infinity
        //     for each vertex V in G.vertices do: H.Insert(V)
        //     // Main loop
        //     while H is not empty do:
        //         w* = H.ExtractMin()
        //         X.Add(w*)
        //         len(w*) = key(w*)
        //         // Update Heap to maintain Invariant
        //         for every edge(w*, y) do:
        //             H.Delete(y)     // Delete: given a heap H and a pointer to an object y in H, delete y from H.
        //             key(y) = min {key(y), len(w*) + l(w*y)}
        //             H.Insert(y)
        public static int[] DijkstraMinHeap(IDirectedWeightedGraph <int> weightedGraph, int startVertex)
        {
            var minHeap          = new IndexMinHeap <int>(weightedGraph.VerticesCount);
            var exploredVertices = new HashSet <int> {
                startVertex
            };
            var len = new int[weightedGraph.VerticesCount + 1];

            for (int i = 1; i <= weightedGraph.VerticesCount; i++)
            {
                var score = i == startVertex ? 0 : 1000000;
                len[i] = score;
                minHeap.Insert(i, score);
            }

            while (!minHeap.IsEmpty())
            {
                int u = minHeap.GetMin();
                len[u] = minHeap.GetItemKey(u);
                minHeap.ExtractMin();
                exploredVertices.Add(u);

                foreach ((int v, int weight) in weightedGraph.GetAdjacentVertices(u))
                {
                    if (!exploredVertices.Contains(v))
                    {
                        if (len[v] > len[u] + weight)
                        {
                            int vKey     = minHeap.GetItemKey(v);
                            int newScore = Math.Min(len[u] + weight, vKey);
                            // can use (minHeap.Delete + minHeap.Insert) instead of DecreaseKey
                            // but this would be less effective
                            minHeap.DecreaseKey(v, newScore);
                            len[v] = newScore;
                        }
                    }
                }
            }

            return(len);
        }
Esempio n. 4
0
 /// <summary>
 /// Traverses graph from start vertex.
 /// </summary>
 /// <param name="graph">Graph instance.</param>
 /// <param name="startVertex">Vertex that search starts from.</param>
 /// <param name="action">Action that needs to be executed on each graph vertex.</param>
 public void VisitAll(IDirectedWeightedGraph <T> graph, Vertex <T> startVertex, Action <Vertex <T> >?action = default)
 {
     Dfs(graph, startVertex, action, new HashSet <Vertex <T> >());
 }
Esempio n. 5
0
 private static (int vertex, int weight) FindMinWeightVertex(IDirectedWeightedGraph <int> weightedGraph, (int tail, int head, int weight) edge)