private static void pickSeeds(IList <IBoundable <IExtents> > items, IBoundable <IExtents>[] group1, IBoundable <IExtents>[] group2) { Int32 group1Count = 0, group2Count = 0; Double largestWaste = -1; ComputationExtents[] allExtents = new ComputationExtents[items.Count]; Int32 itemCount = items.Count; // read the bounds into local structures only once // for speed for (Int32 i = 0; i < itemCount; i++) { allExtents[i] = new ComputationExtents(items[i].Bounds); } Int32 seed1Index = -1, seed2Index = -1; for (Int32 i = 0; i < itemCount; i++) { for (int j = 0; j < itemCount; j++) { if (i == j) { continue; } ComputationExtents e1 = allExtents[i]; ComputationExtents e2 = allExtents[j]; ComputationExtents minBoundingRectangle = e1.Union(e2); ComputationExtents intersection = e1.Intersection(e2); Double minBoundingArea = minBoundingRectangle.Area; Double entry1Area = e1.Area; Double entry2Area = e2.Area; Double waste = (minBoundingArea - entry1Area - entry2Area) + intersection.Area; if (group1Count == 0 && group2Count == 0) { group1[group1Count++] = items[i]; group2[group2Count++] = items[j]; seed1Index = i; seed2Index = j; largestWaste = waste; continue; } if (waste > largestWaste) { group1[0] = items[i]; group2[0] = items[j]; seed1Index = i; seed2Index = j; largestWaste = waste; } } } if (seed1Index > seed2Index) { items.RemoveAt(seed1Index); items.RemoveAt(seed2Index); } else { items.RemoveAt(seed2Index); items.RemoveAt(seed1Index); } }