static uint[] VerticesInPartition = new uint[33]; // One senitel element static void GenerateCuts(int cutIndex, int pos, PartialSolution solution, uint[] column, Vertex[] vertices) { int partitionChecker = 0; int partitionCount = 0; int zeroID = solution.Find(vertices[0].Color); for (int i = 1; i < vertices.Length; i++) { int id = solution.Find(vertices[i].Color); if (id == zeroID) { continue; // The connected component containing vertex 0 is fixed (representative is always lowest vertex) } int mask = 1 << id; if ((partitionChecker & mask) == 0) { partitionChecker |= mask; RootIndex[id] = partitionCount++; VerticesInPartition[RootIndex[id]] = 1u << (i - 1); } else { VerticesInPartition[RootIndex[id]] |= 1u << (i - 1); } } uint cut = 0; for (uint i = 0; i < (1 << partitionCount); i++) { uint delta = i ^ (i + 1); column[cut >> 5] |= 1u << (int)(cut & 31); int j = 0; while (delta != 0) { cut ^= VerticesInPartition[j]; j++; delta >>= 1; } } }
// Old, slower, recursive method of generating a cut void GenerateCuts_old(int cutIndex, int pos, PartialSolution solution, uint[] column, Vertex[] vertices) { if (pos >= vertices.Length) { column[cutIndex >> 5] |= 1u << (cutIndex & 31); return; } bool canGoLeft = true, canGoRight = true; if (solution.Find(vertices[0].Color) == solution.Find(vertices[pos].Color)) { canGoRight = false; } for (int i = 1; i < pos; i++) { if (solution.Find(vertices[i].Color) == solution.Find(vertices[pos].Color)) { if ((cutIndex & (1 << (i - 1))) > 0) { canGoLeft = false; } else { canGoRight = false; } } } if (canGoLeft) { GenerateCuts_old(cutIndex, pos + 1, solution, column, vertices); } if (canGoRight) { GenerateCuts_old(cutIndex | (1 << (pos - 1)), pos + 1, solution, column, vertices); } }
public override bool Equals(object obj) { if (obj == null) { return(false); } PartialSolution objSol = (PartialSolution)obj; if (Subset.LocalSubset != objSol.Subset.LocalSubset) { return(false); } for (int i = 0; i < UnionFind.Length; i++) { if (Find(i) != objSol.Find(i)) { return(false); } } return(true); }