public IEnumerable <(IPhenotype, IPhenotype)> SelectParents(Population population, int n, EAMode mode, IRandomNumberGenerator random) { var roulette = new AliasRoulette <IPhenotype>(random, population, population.GetProbabilitySelector(mode)); for (int i = 0; i < n; i++) { yield return(roulette.Spin(), roulette.Spin()); } }
private const double S = 1; // I think this is configurable, but keep it as is until we are sure. public IEnumerable <(IPhenotype, IPhenotype)> SelectParents(Population population, int n, EAMode mode, IRandomNumberGenerator random) { var std = population.Select(p => p.Fitness).StandardDeviation(); var avg = population.Select(p => p.Fitness).Average(); var roulette = new AliasRoulette <IPhenotype>(random, population, p => S + (p.Fitness - avg) / (2 * std)); for (int i = 0; i < n; i++) { yield return(roulette.Spin(), roulette.Spin()); } }
public IEnumerable <(IPhenotype, IPhenotype)> SelectParents(Population population, int n, EAMode mode, IRandomNumberGenerator random) { if (!population.IsSorted) { throw new ArgumentException("Population is not sorted"); } var roulette = new AliasRoulette <IPhenotype>(random, population, (p, i) => GetProb(i, population.Size)); for (int i = 0; i < n; i++) { yield return(roulette.Spin(), roulette.Spin()); } }
private void AssertCount(IReadOnlyList <Entry> elements, int spins = 0) { var probabilitySum = elements.Select(e => e.Probability).Sum(); if (spins == 0) { var p_min = elements.Min(e => e.Probability); spins = (int)(1000 / (p_min / probabilitySum)); } Console.WriteLine($"spins: {spins}"); var roulette = new AliasRoulette <Entry>(random, elements, e => e.Probability); for (int i = 0; i < spins; i++) { roulette.Spin().Count++; } foreach (var element in elements) { var expectedCount = (element.Probability / probabilitySum) * spins; var actualCount = (double)element.Count; actualCount.Should().BeApproximately(expectedCount, expectedCount * 0.1 + 10); //var expectedProbability = element.Probability / probabilitySum; //var actualProbability = element.Count / (double)spins; //actualProbability.Should().BeApproximately(expectedProbability, expectedProbability * 0.05); } }