public static void Colouring(DrawingSurface ds) { if (!ds.IsUndirected()) { var err = new ErrorBox("Graph has to be unoriented"); err.ShowDialog(); return; } var rnd = new Random { }; var adjList = ds.GetAdjList(); List <int> nodePowers = ds.GetNodePowers(); List <int> vertices = Enumerable.Range(0, ds.Vertices.Count).OrderByDescending(u => nodePowers[u]).ToList(); List <int> colors_list = Enumerable.Repeat(-1, ds.Vertices.Count).ToList(); int colors_used = 1; colors = colors.OrderBy(x => rnd.Next()).ToArray(); colors_list[vertices[0]] = 0; foreach (var vertex in vertices) { if (vertex == vertices[0]) { continue; } var adjacentColors = new HashSet <int> { }; foreach (var adjvertices in adjList[vertex]) { if (colors_list[adjvertices] != -1) { adjacentColors.Add(colors_list[adjvertices]); } } HashSet <int> possibleColors = colors_list.Where(u => u != -1).Except(adjacentColors).ToHashSet(); if (possibleColors.Count == 0) { colors_used += 1; colors_list[vertex] = colors_used - 1; } else { if (colors_list[vertex] == -1) { colors_list[vertex] = possibleColors.Min(); } } } foreach (var vertex in vertices) { ReDrawCircle(ds, vertex, colors[colors_list[vertex]]); } Thread.Sleep(5000); ClearVertices(ds); }
public static void FordFulkerson(DrawingSurface ds) { if (ds.IsUndirected()) { var err = new ErrorBox("Graph have to be directed!"); err.ShowDialog(); return; } if (ds.ContainsNegativeEdge()) { var err = new ErrorBox("Graph can not contain negative edges!"); err.ShowDialog(); return; } Dictionary <int, List <Edge> > adjList = ds.GetDestAdjList(); (var source, var sink) = GetSourceAndSink(adjList); if (source == -1 || sink == -1) { var err = new ErrorBox("Graph have to contain source and sink!"); err.ShowDialog(); return; } ; var fulkersonItems = new FulkersonItem[adjList.Count, adjList.Count]; var minimalFlow = .0; var flows = new List <double>(); msg.MoveToCorner(ds.FindForm() as Form1); msg.SetTitle("Ford-Fulkerson algorithm result:\n"); msg.StartMenu(); for (var i = 0; i < adjList.Count; ++i) { for (var j = 0; j < adjList.Count; ++j) { fulkersonItems[i, j] = new FulkersonItem(); } } for (var start = 0; start < adjList.Count; ++start) { foreach (var edge in adjList[start]) { fulkersonItems[start, edge.end].toFlow = edge.w; edge.SetLabel($"{edge.w}/{0}"); } } while (minimalFlow != -1) { ds.Vertices[source].fillColor = Color.Green; ds.Vertices[sink].fillColor = Color.Red; ds.Invalidate(); minimalFlow = ProcessFulkerson(source, sink, adjList, ref fulkersonItems, ds); if (minimalFlow != -1) { flows.Add(minimalFlow); } ClearVertices(ds); ClearEdges(ds, false); } AlgorithmDone(ds); msg.AddText($"Total maximal flow:\n"); msg.AddText("f(G) = "); for (var i = 0; i < flows.Count; ++i) { msg.AddText($"{flows[i]} "); if (i != flows.Count - 1) { msg.AddText("+ "); } Thread.Sleep(700); } msg.AddText($"= {flows.Sum()}"); msg.WaitOne(); ClearVertices(ds); ClearEdges(ds, true); }
public static void BackTrackingColouring(DrawingSurface ds, int colorAmount) { bool isSafe(int[,] adjmat, int[] color) { for (var i = 0; i < ds.Vertices.Count; ++i) { for (var j = i + 1; j < ds.Vertices.Count; ++j) { if (adjmat[i, j] == 1 && color[j] == color[i]) { return(false); } } } return(true); } bool GraphColouring(int[,] adjmat, int bound, int index, int[] color) { if (index == ds.Vertices.Count) { if (isSafe(adjmat, color)) { for (var k = 0; k < ds.Vertices.Count; ++k) { ReDrawCircle(ds, k, colors[color[k]]); } return(true); } return(false); } for (var j = 1; j <= bound; ++j) { color[index] = j; if (GraphColouring(adjmat, bound, index + 1, color)) { return(true); } color[index] = 0; } return(false); } var adjMatrix = ds.GetAdjMatrix(); var colorsList = new List <int> { }; if (!ds.IsUndirected()) { var err = new ErrorBox("Graph has to be unoriented"); err.ShowDialog(); return; } for (var i = 0; i < ds.Vertices.Count; ++i) { colorsList.Add(0); } if (!GraphColouring(adjMatrix, colorAmount, 0, colorsList.ToArray())) { var err = new ErrorBox($"Graph cannot be coloured into {colorAmount} colours"); err.ShowDialog(); return; } Thread.Sleep(5000); ClearVertices(ds); }