public static E AddEdge( IWeightedGraph <V, E> graph, V sourceVertex, V targetVertex, double weight) { var edge = graph.EdgeFactory.CreateEdge(sourceVertex, targetVertex); graph.SetEdgeWeight(edge, weight); return(graph.AddEdge(sourceVertex, targetVertex, edge) ? edge : default(E)); }
public ReadWeightedGraph(IWeightedGraph <double> graph, string filename) { string[] lines = File.ReadAllLines(@"G:\Project\Play-with-Data-Structures\C#\DS_Graph\WeightedGraph\" + filename); int V = graph.V(); int E = graph.E(); for (int i = 1; i < lines.Length; i++) { int v = Convert.ToInt32(lines[i].Split(' ')[0]); int w = Convert.ToInt32(lines[i].Split(' ')[1]); double wt = Convert.ToDouble(lines[i].Split(' ')[2]); graph.AddEdge(new Edge <double>(v, w, wt)); } }
/** * Finds a minimum spanning tree in the graph. * * @note The MST is computed using the Prim's (also knows as DJP) * algorithm. * TODO: describe the algorithm * * @param mst Unweighted tree instance that will become * an MST in this method. The MST instance must * already contain all the original's graph * vertices. * * @return The weighted graph instance representing the MST. Note * that NULL is returned if the graph is disconnected (in other * words, there is not path from any given vertex to all other * vertices in the graph). * * @throws InvalidOperationException if graph is empty. */ protected IWeightedGraph <VertexT> FindMinimumSpanningTree(IWeightedGraph <VertexT> mst) { if (Size == 0) { // It is illegal to call this method on an empty graph throw new InvalidOperationException(); } // Priority queue that orders the edges in ascending order // by their weight. The next edge to place into MST is // taken from the priority queue. ArrayHeap <Edge> priority_queue = new ArrayHeap <Edge>( Size, (Edge edge_1, Edge edge_2) => { // TODO: floats shouldn't be compared like this. if (edge_1.Weight < edge_2.Weight) { return(-1); } else if (edge_1.Weight > edge_2.Weight) { return(1); } else { return(0); } }); // A vertex is 'marked' once an edge ending in that vertex // has been added to MST, that is once vertex becomes part // of the MST. This helps ensure that we never add two edges // that end in the same vertex, which in turn makes sure // that generated graph is in fact a MST. BitArray marked_vertices = new BitArray(Size, false); marked_vertices[0] = true; // The vertex whose outward edges will be processed next int vertex_index = 0; // The following loop will run Size - 1 times, as we need // to select Size - 1 edges for (int i = 1; i < Size; ++i) { for (int column = 0; column < Size; ++column) { float?edge_value = Edges.GetEdge(vertex_index, column); if (edge_value != null && !marked_vertices[column]) { // Add this edge to the priority queue priority_queue.Insert(new Edge(vertex_index, column, edge_value.Value)); } } // Find the next edge to insert to the MST. We cannot simply pick // an edge at the head of the priority queue because the end // vertex of that edge might already be 'marked', hence edges // towards it must not be considered Edge min_weight_edge = null; do { if (priority_queue.IsEmpty) { // This means that we're unable to reach all vertices // of the graph (disconnected graph). Return NULL. return(null); } min_weight_edge = priority_queue.Remove(); } while (marked_vertices[min_weight_edge.EndVertex]); // Add the edge to the MST mst.AddEdge( min_weight_edge.StartVertex, min_weight_edge.EndVertex, min_weight_edge.Weight); // 'Mark' the end vertex of the newly added edge marked_vertices[min_weight_edge.EndVertex] = true; // The next vertex whose outward edges will be processed is // the end vertex of the edge we just added to MST vertex_index = min_weight_edge.EndVertex; } return(mst); }