static public PuzzleArea Join(PuzzleArea areaA, PuzzleArea areaB) { // Sicherstellen, dass beide Mengen gleich groß sind!!! if (!areaA.PositionsEquals(areaB)) { return(null); } PuzzleArea result = Clone(areaA); result.MinFilled = Math.Max(areaA.MinFilled, areaB.MinFilled); result.MaxFilled = Math.Min(areaA.MaxFilled, areaB.MaxFilled); result.MinEmpty = Math.Max(areaA.MinEmpty, areaB.MinEmpty); result.MaxEmpty = Math.Min(areaA.MaxEmpty, areaB.MaxEmpty); result.RefreshDistincts(); foreach (Point pos in areaA.InvolvedNumberPositions) { if (!result.InvolvedNumberPositions.Contains(pos)) { result.InvolvedNumberPositions.Add(pos); } } foreach (Point pos in areaB.InvolvedNumberPositions) { if (!result.InvolvedNumberPositions.Contains(pos)) { result.InvolvedNumberPositions.Add(pos); } } return(result); }
static public List <PuzzleArea> Join(List <PuzzleArea> areas) { List <PuzzleArea> result = new List <PuzzleArea>(); result.AddRange(areas); for (int i = 0; i < result.Count; i++) { PuzzleArea areaA = result[i]; int j = i + 1; while (j < result.Count) { PuzzleArea areaB = result[j]; if (areaA.PositionsEquals(areaB)) { result[i] = Join(areaA, areaB); result.RemoveAt(j); } else { j++; } } } return(result); }
static public PuzzleArea Subset(PuzzleArea areaA, PuzzleArea areaB) { PuzzleArea result = Differenz(areaA, areaB); if (result != null) { result.MaxFilled = Math.Min(areaA.MinFilled - areaB.MinFilled, result.Positions.Count); result.MinFilled = Math.Min(areaA.MaxFilled - areaB.MaxFilled, result.Positions.Count); result.MaxEmpty = Math.Min(areaA.MinEmpty - areaB.MinEmpty, result.Positions.Count); result.MinEmpty = Math.Min(areaA.MaxEmpty - areaB.MaxEmpty, result.Positions.Count); result.RefreshDistincts(); foreach (Point pos in areaA.InvolvedNumberPositions) { if (!result.InvolvedNumberPositions.Contains(pos)) { result.InvolvedNumberPositions.Add(pos); } } foreach (Point pos in areaB.InvolvedNumberPositions) { if (!result.InvolvedNumberPositions.Contains(pos)) { result.InvolvedNumberPositions.Add(pos); } } } return(result); }
static public PuzzleArea Clone(PuzzleArea original) { PuzzleArea result = new PuzzleArea(original.Board); foreach (Point pos in original.Positions) { result.AddPosition(pos); } return(result); }
static public List <PuzzleArea> Split(List <PuzzleArea> areas) { List <int> indexes = new List <int>(); List <PuzzleArea> splittedAreas = new List <PuzzleArea>(); for (int i = 0; i < areas.Count; i++) { PuzzleArea areaA = areas[i]; bool foundSplit = false; for (int j = i + 1; j < areas.Count; j++) { PuzzleArea areaB = areas[j]; if (HasOverlap(areaA, areaB) && !areaA.PositionsEquals(areaB)) { PuzzleArea overlapA = Overlap(areaA, areaB); PuzzleArea overlapB = Overlap(areaB, areaA); PuzzleArea overlapAB = Join(overlapA, overlapB); PuzzleArea leftA = Subset(areaA, overlapAB); PuzzleArea rightB = Subset(areaB, overlapAB); if (!indexes.Contains(i)) { indexes.Add(i); } if (!indexes.Contains(j)) { indexes.Add(j); } if (leftA != null && leftA.Positions.Count > 1) { splittedAreas.Add(leftA); foundSplit = true; } if (overlapAB != null && overlapAB.Positions.Count > 1) { splittedAreas.Add(overlapAB); foundSplit = true; } if (rightB != null && rightB.Positions.Count > 1) { splittedAreas.Add(rightB); foundSplit = true; } } } if (!foundSplit) { splittedAreas.Add(areaA); } } List <PuzzleArea> joindAreas = CleanUp(Join(splittedAreas)); return(CleanUp(joindAreas)); }
static public bool HasOverlap(PuzzleArea areaA, PuzzleArea areaB) { foreach (Point pos in areaA.Positions) { if (areaB.Positions.Contains(pos)) { return(true); } } return(false); }
static public PuzzleArea Differenz(PuzzleArea areaA, PuzzleArea areaB) { PuzzleArea result = new PuzzleArea(areaA.Board); PuzzleArea overlap = Overlap(areaA, areaB); foreach (Point pos in areaA.Positions) { if (!areaB.Positions.Contains(pos)) { result.AddPosition(pos); } } PuzzleArea areaRightB = new PuzzleArea(areaB.Board); foreach (Point pos in areaB.Positions) { if (!areaA.Positions.Contains(pos)) { areaRightB.AddPosition(pos); } } if (result.Positions.Count == 0) { return(null); } result.MinFilled = Math.Max(result.Positions.Count, areaA.MinFilled - overlap.MaxFilled - areaRightB.MinFilled); result.MaxFilled = Math.Min(result.Positions.Count, areaA.MaxFilled - overlap.MinFilled - areaRightB.MaxFilled); result.MinEmpty = Math.Max(result.Positions.Count, areaA.MinEmpty - overlap.MaxEmpty - areaRightB.MinEmpty); result.MaxEmpty = Math.Min(result.Positions.Count, areaA.MaxEmpty - overlap.MinEmpty - areaRightB.MaxEmpty); result.RefreshDistincts(); foreach (Point pos in areaA.InvolvedNumberPositions) { if (!result.InvolvedNumberPositions.Contains(pos)) { result.InvolvedNumberPositions.Add(pos); } } foreach (Point pos in areaB.InvolvedNumberPositions) { if (!result.InvolvedNumberPositions.Contains(pos)) { result.InvolvedNumberPositions.Add(pos); } } return(result); }
public bool PositionsEquals(PuzzleArea compare) { if (Positions.Count != compare.Positions.Count) { return(false); } foreach (Point pos in Positions) { if (!compare.Positions.Contains(pos)) { return(false); } } return(true); }
static public PuzzleArea Overlap(PuzzleArea areaA, PuzzleArea areaB) { PuzzleArea result = new PuzzleArea(areaA.Board); PuzzleArea leftAreaA = new PuzzleArea(areaA.Board); foreach (Point pos in areaA.Positions) { if (areaB.Positions.Contains(pos)) { result.AddPosition(pos); } else { leftAreaA.AddPosition(pos); } } if (result.Positions.Count == 0) { return(null); } result.MinFilled = Math.Max(0, areaA.MinFilled - leftAreaA.UndefinedCount - leftAreaA.FilledCount); result.MaxFilled = Math.Min(areaA.MaxFilled, result.UndefinedCount + result.FilledCount); result.MinEmpty = Math.Max(0, areaA.MinEmpty - leftAreaA.UndefinedCount - leftAreaA.EmptyCount); result.MaxEmpty = Math.Min(areaA.MaxEmpty, result.UndefinedCount + result.EmptyCount); result.RefreshDistincts(); foreach (Point pos in areaA.InvolvedNumberPositions) { if (!result.InvolvedNumberPositions.Contains(pos)) { result.InvolvedNumberPositions.Add(pos); } } foreach (Point pos in areaB.InvolvedNumberPositions) { if (!result.InvolvedNumberPositions.Contains(pos)) { result.InvolvedNumberPositions.Add(pos); } } return(result); }