// Assign all points to nearest cluster public void UpdatePointsByCentroid() // O(n*k) { // Clear points in the buckets, they will be re-inserted foreach (var bucket in BucketsLookup.Values) { bucket.Points.Clear(); } foreach (var p in this.points) { var minDist = Double.MaxValue; var index = string.Empty; foreach (var i in BucketsLookup.Keys) { var bucket = BucketsLookup[i]; if (bucket.IsUsed == false) { continue; } var centroid = bucket.Centroid; var dist = MathTool.Distance(p, centroid); if (dist < minDist) { // update minDist = dist; index = i; } } // re-insert var closestBucket = BucketsLookup[index]; closestBucket.Points.Add(p); } }
static double RunOneIteration() //O(k*n) { GlobalClass.program += "35. Runoneiteration .. "; // update points, assign points to cluster UpdatePointsByCentroid(); // update centroid pos by its points BaseSetCentroidForAllBuckets(BaseBucketsLookup.Values);//O(k*n) var clustersCount = BaseBucketsLookup.Count; for (int i = 0; i < clustersCount; i++) { var currentBucket = BaseBucketsLookup[i.ToString()]; if (currentBucket.IsUsed == false) { continue; } //update centroid var newcontroid = BaseGetCentroidFromCluster(currentBucket.Points); //no need to update CGroup, autoset currentBucket.Centroid = newcontroid; currentBucket.ErrorLevel = 0; //update error foreach (var p in currentBucket.Points) { var dist = MathTool.Distance(newcontroid, p); currentBucket.ErrorLevel += dist; } var val = currentBucket.ErrorLevel / currentBucket.Points.Count; currentBucket.ErrorLevel = val; //Math.Sqrt(val); } Profile("RunOneIteration"); return(BaseGetTotalError()); }
public void DistanceTest(double x1, double y1, double x2, double y2) { Assert.AreEqual(x2.Hypot2(y2), MathTool.Distance(x1, y1, x2, y2), 0.000000001d); var p1 = new PointF((float)x1, (float)y1); var p2 = new PointF((float)x2, (float)y2); Assert.AreEqual(x2.Hypot2(y2), p1.Distance(p2), 0.000000001d); }
private static Segment MyClosestRec(List <XY> pointsByX) { int count = pointsByX.Count; if (count <= 4) { return(Segment.Closest_BruteForce(pointsByX)); } // left and right lists sorted by X, as order retained from full list var leftByX = pointsByX.Take(count / 2).ToList(); var leftResult = MyClosestRec(leftByX); var rightByX = pointsByX.Skip(count / 2).ToList(); var rightResult = MyClosestRec(rightByX); var result = rightResult.Length() < leftResult.Length() ? rightResult : leftResult; // There may be a shorter distance that crosses the divider // Thus, extract all the points within result.Length either side var mxid = leftByX.Last().X; var bandWidth = result.Length(); var inBandByX = pointsByX.Where(p => Math.Abs(mxid - p.X) <= bandWidth); // Sort by Y, so we can efficiently check for closer pairs var inBandByY = inBandByX.OrderBy(p => p.Y).ToArray(); int iLast = inBandByY.Length - 1; for (int i = 0; i < iLast; i++) { var pLower = inBandByY[i]; for (int j = i + 1; j <= iLast; j++) { var pUpper = inBandByY[j]; // Comparing each point to successivly increasing Y values // Thus, can terminate as soon as deltaY is greater than best result if ((pUpper.Y - pLower.Y) >= result.Length()) { break; } if (MathTool.Distance(pLower, pUpper) < result.Length()) { result = new Segment(pLower, pUpper); } } } return(result); }
void MergeClustersGridHelper(string currentKey, string[] neighborKeys) { GlobalClass.program += "41. GridBaseCluster.MergeClustersGridHelper .. "; double minDistX = DeltaX / 2.0;//heuristic, higher value gives less merging double minDistY = DeltaY / 2.0; //if clusters in grid are too close to each other, merge them double minDist = MathTool.Max(minDistX, minDistY); foreach (var neighborKey in neighborKeys) { if (!BaseBucketsLookup.ContainsKey(neighborKey)) { continue; } var neighbor = BaseBucketsLookup[neighborKey]; if (neighbor.IsUsed == false) { continue; } var current = BaseBucketsLookup[currentKey]; var dist = MathTool.Distance(current.Centroid, neighbor.Centroid); if (dist > minDist) { continue; } var centroidgroup = current.Centroid.CGroup; foreach (var p in neighbor.Points) { //update CGroup p.CGroup = centroidgroup; }//end neighP = neighbor.Points.ToArray(); current.Points.AddRange(neighbor.Points);//O(n) // recalc centroid var cp = BaseGetCentroidFromCluster(current.Points); current.Centroid = cp; neighbor.IsUsed = false; //merged, then not used anymore } }
void MergeClustersGridHelper(string currentKey, string[] neighborKeys) { double minDistX = DeltaX / 2.0; //heuristic, higher value gives less merging double minDistY = DeltaY / 2.0; //if clusters in grid are too close to each other, merge them double minDist = MathTool.Max(minDistX, minDistY); foreach (var neighborKey in neighborKeys) { if (!BaseBucketsLookup.ContainsKey(neighborKey)) { continue; } var neighbor = BaseBucketsLookup[neighborKey]; if (neighbor.IsUsed == false) { continue; } var current = BaseBucketsLookup[currentKey]; var dist = MathTool.Distance(current.Centroid, neighbor.Centroid); if (dist > minDist) { continue; } // merge var color = current.Centroid.Color; foreach (var p in neighbor.Points) { //update color p.Color = color; } current.Points.AddRange(neighbor.Points); //O(n) // recalc centroid var cp = BaseGetCentroidFromCluster(current.Points); current.Centroid = cp; neighbor.IsUsed = false; //merged, then not used anymore neighbor.Points.Clear(); //clear mem } }
public MapPoint GetClosestPoint(MapPoint from, List <MapPoint> list) // O(n) { var min = double.MaxValue; MapPoint closests = null; foreach (var p in list) { var dist = MathTool.Distance(from, p); if (dist >= min) { continue; } // update min = dist; closests = p; } return(closests); }
public XY BaseGetLongestPoint(XY from, List <XY> list) //O(n) { double max = -double.MaxValue; XY longest = null; foreach (var p in list) { var d = MathTool.Distance(from, p); if (d <= max) { continue; } // update max = d; longest = p; } return(longest); }
public static XY BaseGetClosestPoint(XY from, List <XY> list) //O(n) { double min = double.MaxValue; XY closests = null; foreach (var p in list) { var d = MathTool.Distance(from, p); if (d >= min) { continue; } // update min = d; closests = p; } return(closests); }
public IP GetClosestPoint(IP from, IPoints list) // O(n) { var min = double.MaxValue; IP closests = null; foreach (var p in list.Data) { var d = MathTool.Distance(from, p); if (d >= min) { continue; } // update min = d; closests = p; } return(closests); }
public static XY BaseGetLongestPoint(XY from, List <XY> list) //O(n) { GlobalClass.program += "27. BaseClusternewKmeans.BaeGetLongestPoint .. "; double max = -double.MaxValue; XY longest = null; foreach (var p in list) { var d = MathTool.Distance(from, p); if (d <= max) { continue; } // update max = d; longest = p; } return(longest); }
public static XY BaseGetClosestPoint(XY from, List <XY> list) //O(n) { GlobalClass.program += "26. BaseClusternewKmeans.BaseGetClosestPoint .. "; double min = double.MaxValue; XY closests = null; foreach (var p in list) { var d = MathTool.Distance(from, p); if (d >= min) { continue; } // update min = d; closests = p; } return(closests); }
static void UpdatePointsByCentroid()//O(n*k) { GlobalClass.program += "36. Updatepointsbycentroid.. "; int count = BaseBucketsLookup.Count(); // clear points in the buckets, they will be re-inserted foreach (var bucket in BaseBucketsLookup.Values) { bucket.Points.Clear(); } foreach (XY p in BaseDataset) { double minDist = Double.MaxValue; int index = -1; for (int i = 0; i < count; i++) { var bucket = BaseBucketsLookup[i.ToString()]; if (bucket.IsUsed == false) { continue; } var centroid = bucket.Centroid; var dist = MathTool.Distance(p, centroid); if (dist < minDist) { // update minDist = dist; index = i; } } //update CGroup for point to match centroid and re-insert var closestBucket = BaseBucketsLookup[index.ToString()]; p.CGroup = closestBucket.Centroid.CGroup; closestBucket.Points.Add(p); } Profile("UpdatePointsByCentroid"); }
// assign all points to nearest cluster public void BaseUpdatePointsByCentroid() //O(n*k) { Profile("UpdatePointsByCentroid beg"); int count = BaseBucketsLookup.Count(); // clear points in the buckets, they will be re-inserted foreach (var bucket in BaseBucketsLookup.Values) { bucket.Points.Clear(); } foreach (XY p in BaseDataset) { double minDist = Double.MaxValue; string index = string.Empty; //for (int i = 0; i < count; i++) foreach (var i in BaseBucketsLookup.Keys) { var bucket = BaseBucketsLookup[i]; if (bucket.IsUsed == false) { continue; } var centroid = bucket.Centroid; var dist = MathTool.Distance(p, centroid); if (dist < minDist) { // update minDist = dist; index = i; } } //update color for point to match centroid and re-insert var closestBucket = BaseBucketsLookup[index]; p.Color = closestBucket.Centroid.Color; closestBucket.Points.Add(p); } }
void MergeClustersGridHelper(string currentKey, IEnumerable <string> neighborKeys) { double minDistX = DeltaX / GmcSettings.Get.MergeWithin; double minDistY = DeltaY / GmcSettings.Get.MergeWithin; // If clusters in grid are too close to each other, merge them double withinDist = Math.Max(minDistX, minDistY); foreach (var neighborKey in neighborKeys) { if (!BucketsLookup.ContainsKey(neighborKey)) { continue; } var neighbor = BucketsLookup[neighborKey]; if (neighbor.IsUsed == false) { continue; } var current = BucketsLookup[currentKey]; var dist = MathTool.Distance(current.Centroid, neighbor.Centroid); if (dist > withinDist) { continue; } current.Points.AddRange(neighbor.Points); //O(n) // recalc centroid var centroidPoint = GetCentroidFromClusterLatLon(current.Points); current.Centroid = centroidPoint; neighbor.IsUsed = false; // merged, then not used anymore neighbor.Points.Clear(); // clear mem } }
public void DistanceTest() { Assert.AreEqual(5, MathTool.Distance(0, 0, 3, 4, 1)); }