/** * Filters the graph so that only entities connected to the root are left * * Should be run after you've added some set of associations with from() * * @return void */ public function filterConnected() { $alg = new BreadthFirst($this->graph->getVertex($this->root)); $alg->setDirection(BreadthFirst::DIRECTION_REVERSE); $vertices = $alg->getVertices(); $this->graph = $this->graph->createGraphCloneVertices($vertices); }
/** * * @return Edges */ public function getEdges() { $returnEdges = array(); // Create minimum spanning tree $minimumSpanningTreeAlgorithm = new MstKruskal($this->graph); $minimumSpanningTree = $minimumSpanningTreeAlgorithm->createGraph(); $alg = new SearchDepthFirst($minimumSpanningTree->getVertices()->getVertexFirst()); // Depth first search in minmum spanning tree (for the eulerian path) $startVertex = NULL; $oldVertex = NULL; // connect vertices in order of the depth first search foreach ($alg->getVertices() as $vertex) { // get vertex from the original graph (not from the depth first search) $vertex = $this->graph->getVertex($vertex->getId()); // need to clone the edge from the original graph, therefore i need the original edge if ($startVertex === NULL) { $startVertex = $vertex; } else { // get edge(s) to clone, multiple edges are possible (returns an array if undirected edge) $returnEdges[] = $oldVertex->getEdgesTo($vertex)->getEdgeFirst(); } $oldVertex = $vertex; } // connect last vertex with start vertex // multiple edges are possible (returns an array if undirected edge) $returnEdges[] = $oldVertex->getEdgesTo($startVertex)->getEdgeFirst(); return new Edges($returnEdges); }
/** * * @param Vertex $vertex * @return SearchBreadthFirst */ private function createSearch(Vertex $vertex) { $alg = new SearchBreadthFirst($vertex); // follow into both directions (loosely connected) return $alg->setDirection(SearchBreadthFirst::DIRECTION_BOTH); }
/** * * * @param Vertex $source * @throws Exception if there is no reachable sink vertex * * @return Vertex a sink-vertex that is reachable from the source * @uses BreadthFirst::getVertices() */ private function getVertexSink(Vertex $source) { // search for reachable Vertices $algBFS = new SearchBreadthFirst($source); foreach ($algBFS->getVertices()->getMap() as $vid => $vertex) { if ($this->graph->getVertex($vid)->getBalance() - $vertex->getBalance() < 0) { return $vertex; } } throw new UnderflowException('No sink vertex connected to given source vertex found'); }