public static TreeNode <Point2d> MakeBfsTree(Point2d rootPt, Func <Point2d, bool> isInDomain) { TreeNode <Point2d> root = new TreeNode <Point2d>(rootPt); PointSet2d alreadyIncluded = new PointSet2d(); alreadyIncluded.Add(root.value); Point2d[] neighbors = new Point2d[8]; Queue <TreeNode <Point2d> > searchSpace = new Queue <TreeNode <Point2d> >(); searchSpace.Enqueue(root); while (searchSpace.Count > 0) { var node = searchSpace.Dequeue(); SetNeighbors(node.value, ref neighbors); for (int idx = 0; idx < neighbors.Length; idx++) { Point2d pt = neighbors[idx]; if (isInDomain(pt) && !alreadyIncluded.Contains(pt)) { searchSpace.Enqueue(new TreeNode <Point2d>(pt, node)); alreadyIncluded.Add(pt); } } } return(root); }
public static Point2d?Bfs(Point2d start, Func <Point2d, bool> isInDomain, Func <Point2d, bool> isSatisfactory) { PointSet2d alreadyIncluded = new PointSet2d(); alreadyIncluded.Add(start); Point2d[] neighbors = new Point2d[8]; Queue <Point2d> searchSpace = new Queue <Point2d>(); searchSpace.Enqueue(start); while (searchSpace.Count > 0) { var current = searchSpace.Dequeue(); SetNeighbors(current, ref neighbors); for (int idx = 0; idx < neighbors.Length; idx++) { Point2d pt = neighbors[idx]; if (isInDomain(pt) && !alreadyIncluded.Contains(pt)) { if (isSatisfactory(pt)) { return(pt); } else { searchSpace.Enqueue(pt); alreadyIncluded.Add(pt); } } } } return(null); }
public static Dictionary <T, HashSet <PointSet2d> > FindContiguousSets <T>(this IField2d <T> field) { Dictionary <T, HashSet <PointSet2d> > categoryToSets = new Dictionary <T, HashSet <PointSet2d> >(); // At the beginning, all points are unaffiliated. PointSet2d unaffiliated = new PointSet2d(); for (int x = 0, y = 0; y < field.Height; y += ++x / field.Width, x %= field.Width) { unaffiliated.Add(new Point2d(x, y)); } Point2d[] neighbors = new Point2d[8]; for (int x = 0, y = 0; y < field.Height; y += ++x / field.Width, x %= field.Width) { Point2d p = new Point2d(x, y); if (unaffiliated.Contains(p)) { // Start a new contiguous set. PointSet2d contiguousSet = new PointSet2d(); T key = field[p.y, p.x]; // Only points which (1) are unaffiliated and (2) have not been considered // for this set are allowed to be candidates. Queue <Point2d> candidates = new Queue <Point2d>(); PointSet2d considered = new PointSet2d(); candidates.Enqueue(p); considered.Add(p); while (candidates.Count > 0) { p = candidates.Dequeue(); if (Object.Equals(field[p.y, p.x], key)) { unaffiliated.Remove(p); contiguousSet.Add(p); Utils.SetNeighbors(p, ref neighbors); for (int idx = 0; idx < neighbors.Length; idx++) { p = neighbors[idx]; if (unaffiliated.Contains(p) && !considered.Contains(p)) { candidates.Enqueue(p); considered.Add(p); } } } } HashSet <PointSet2d> sets; if (!categoryToSets.TryGetValue(key, out sets)) { sets = new HashSet <PointSet2d>(); categoryToSets.Add(key, sets); } sets.Add(contiguousSet); } } return(categoryToSets); }