Skip to content

Instantly share code, notes, and snippets.

@kleberandrade
Created June 9, 2018 02:38
Show Gist options
  • Save kleberandrade/092eba74ecb343254260aeb61d891ac4 to your computer and use it in GitHub Desktop.
Save kleberandrade/092eba74ecb343254260aeb61d891ac4 to your computer and use it in GitHub Desktop.
Algoritmo genético implementa na aula de Inteligência Artificial para Jogos Digitais (x^2)
using System;
using System.Collections.Generic;
namespace GeneticAlgorithmConsoleApp
{
public class Program
{
public static int RANDOM_SEED = 10;
public static Random random = new Random(RANDOM_SEED);
public static List<int[]> CreatePopulation(int chromosomeLength, int populationSize)
{
List<int[]> population = new List<int[]>();
for (int i = 0; i < populationSize; i++)
{
int[] chromosome = new int[chromosomeLength];
for (int j = 0; j < chromosomeLength; j++)
chromosome[j] = random.Next(0, 2);
population.Add(chromosome);
}
return population;
}
public static int ConvertArrayToDecimal(int[] chromosome)
{
int value = 0;
for (int i = 0; i < chromosome.Length; i++)
{
int exp = chromosome.Length - i - 1;
value += (int)Math.Pow(2, exp) * chromosome[i];
}
return value;
}
public static int[] EvaluateFitness(List<int[]> population)
{
int[] fitness = new int[population.Count];
for (int i = 0; i < population.Count; i++)
{
int x = ConvertArrayToDecimal(population[i]);
fitness[i] = x * x;
}
return fitness;
}
public static float[] SelectionProbability(int[] fitness)
{
int sum = 0;
for (int i = 0; i < fitness.Length; i++)
sum += fitness[i];
float[] probability = new float[fitness.Length];
for (int i = 0; i < fitness.Length; i++)
probability[i] = fitness[i] / (float)sum;
return probability;
}
public static int[] Selection(List<int[]> population, int[] fitness)
{
int[] parent = new int[population[0].Length];
float[] probability = SelectionProbability(fitness);
float rouletteNumber = (float)random.NextDouble();
float probabilitiesAccumulation = 0.0f;
for (int i = 0; i < fitness.Length; i++)
{
probabilitiesAccumulation += probability[i];
if (rouletteNumber < probabilitiesAccumulation)
{
Array.Copy(population[i], parent, population[i].Length);
break;
}
}
return parent;
}
public static void Crossover(int[] parent1, int[] parent2, int[] offspring1, int[] offspring2, float crossoverRate)
{
if (random.NextDouble() < crossoverRate)
{
int cutoff = random.Next(1, parent1.Length);
for (int i = 0; i < parent1.Length; i++)
{
offspring1[i] = i < cutoff ? parent1[i] : parent2[i];
offspring2[i] = i < cutoff ? parent2[i] : parent1[i];
}
}
else
{
Array.Copy(parent1, offspring1, parent1.Length);
Array.Copy(parent2, offspring2, parent2.Length);
}
}
public static void Mutation(int[] chromosome, float mutationRate)
{
if (random.NextDouble() < mutationRate)
{
int position = random.Next(0, chromosome.Length);
chromosome[position] = 1 - chromosome[position];
}
}
public static void ShowPopulation(List<int[]> population, int[] fitness, float[] probability, int generation)
{
Console.WriteLine("\nGeneration: #" + generation);
for (int i = 0; i < population.Count; i++)
{
for (int j = 0; j < population[i].Length; j++)
Console.Write(population[i][j]);
Console.Write(" - " + fitness[i].ToString("0000000"));
Console.WriteLine(" - " + (probability[i] * 100.0f).ToString("00.00"));
}
}
public static void Main(string[] args)
{
const int CHROMOSOME_LENGTH = 5;
const int POPULATION_SIZE = 10;
const int MAX_GENERATION = 100;
const float MUTATION_RATE = 0.01f;
const float CROSSOVER_RATE = 0.8f;
int generation = 0;
List<int[]> population = CreatePopulation(CHROMOSOME_LENGTH, POPULATION_SIZE);
int[] fitness = EvaluateFitness(population);
ShowPopulation(population, fitness, SelectionProbability(fitness), generation);
while (generation++ < MAX_GENERATION)
{
List<int[]> newPopulation = new List<int[]>();
while (newPopulation.Count < population.Count)
{
int[] parent1 = Selection(population, fitness);
int[] parent2 = Selection(population, fitness);
int[] offspring1 = new int[parent1.Length];
int[] offspring2 = new int[parent2.Length];
Crossover(parent1, parent2, offspring1, offspring2, CROSSOVER_RATE);
Mutation(offspring1, MUTATION_RATE);
Mutation(offspring2, MUTATION_RATE);
newPopulation.Add(offspring1);
newPopulation.Add(offspring2);
}
population = newPopulation;
fitness = EvaluateFitness(population);
ShowPopulation(population, fitness, SelectionProbability(fitness), generation);
}
Console.ReadKey();
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment