public double GetDistanceToPoint(MarkedPointD point) { return Math.Sqrt( Math.Pow(X - point.X, 2) + Math.Pow(Y - point.Y, 2) ); }
//D(X,y) private double CalculateFieldInPoint(MarkedPointD point) { //if (SourceSet.Any(source => source.X == point.X && source.Y == point.Y)) // return Double.PositiveInfinity; //?????????????????????????????????????????? return SourceSet.Sum(source => SourceActionFunction(Math.Abs(point.GetDistanceToPoint(source)))); }
public static List<MarkedPointD> FindOptimalAllocation( List<MarkedPointD> discreteSet, List<MarkedPointD> initialSourceSet, double discretizationStep, double sourceMovingStep, double stepDecreasingMultiplier, double stepMinimum, double eps ) { DiscreteSet = new DiscreteSet(discreteSet, initialSourceSet); OptimalSourceSet = new List<MarkedPointD>(); foreach (var source in initialSourceSet) { var point = new MarkedPointD(source.X, source.Y); OptimalSourceSet.Add(point); } DiscretizationStep = discretizationStep; SourceMovingStep = sourceMovingStep; StepDecreasingMultiplier = stepDecreasingMultiplier; StepMinimum = stepMinimum; Eps = eps; while (true) { //1 step DiscreteSet.SetFieldValue(); //Расчитываем D в узлах сетки LocalMinimumSet = DiscreteSet.FindLocalMinimums(DiscretizationStep); globalMinimum = DiscreteSet.MinimumFieldValue; //globalMinimum = LocalMinimumSet.Select(point => point.FieldValue).Min(); GlobalMinimumSet = LocalMinimumSet.FindAll(minimum => Math.Abs(minimum.FieldValue - globalMinimum) < Eps); if (LocalMinimumSet.Count == GlobalMinimumSet.Count) break; //Go to step 6 if (globalMinimum < Mu) { SourceMovingStep = SourceMovingStep * StepDecreasingMultiplier; if (SourceMovingStep < StepMinimum) break; //Go to step 6 } else { Mu = globalMinimum; OptimalSourceSet = new List<MarkedPointD>(); foreach (var source in DiscreteSet.SourceSet) { var point = new MarkedPointD(source.X, source.Y); OptimalSourceSet.Add(point); } } //Step 4 foreach (var source in DiscreteSet.SourceSet) { var min = GlobalMinimumSet.FirstOrDefault(m => m.GetDistanceToPoint(source) == GlobalMinimumSet.Select(p => p.GetDistanceToPoint(source)).Min()); var distance = source.GetDistanceToPoint(min); if (SourceMovingStep < distance) { double k = SourceMovingStep / distance; source.X = (source.X + k * min.X) / (1 + k); source.Y = (source.Y + k * min.Y) / (1 + k); } else { double k = distance / SourceMovingStep; source.X = ((1 + k) * min.X - source.X) / k; source.Y = ((1 + k) * min.Y - source.Y) / k; } var nearestPoint = DiscreteSet.Set.FirstOrDefault(s => s.GetDistanceToPoint(source) == DiscreteSet.Set.Select(p => p.GetDistanceToPoint(source)).Min()); source.X = nearestPoint.X; source.Y = nearestPoint.Y; } } return OptimalSourceSet; }
//D(X,y) private double CalculateFieldInPoint(MarkedPointD point, params double[] x) { var SourceSet = new List<MarkedPointD>(); for (int i = 0; i < c / 2; i++) { SourceSet.Add(new MarkedPointD(x[i], x[i + c / 2 - 1])); } if (SourceSet.Any(source => source.X == point.X && source.Y == point.Y)) return Double.PositiveInfinity; return SourceSet.Sum(source => SourceActionFunction(Math.Abs(point.GetDistanceToPoint(source)))); }