private void FirstPopulation() { List <int> freeSpace = new List <int>();//список свободных пар на неделе (6 дней * 6 пар = 36) List <int> weekly = new List <int>(); int x = 0; for (int i = 0; i < 36; i++) { freeSpace.Add(i); weekly.Add(x); x++; if (x > 5) { x = 0; } } //распределение всех пар из стека по дням, то есть распределение хромосом в особи maxStack = lessons.Count; for (int i = 0; i < maxStack; i++) { Lesson freeLesson = lessons.Pop(); //boundLesson.area = // вставить номер кабинета int index = rand.Next(freeSpace.Count); //index в свободных днях для проведения пар int index2 = weekly.ElementAt(index); //по какому счету проводится пара от 0 до 5 int dday = freeSpace.ElementAt(index); //значение свободного дня от 1 до 36 freeSpace.RemoveAt(index); //удаляем из списка свободных дней тот, который уже взяли weekly.RemoveAt(index); int curDay = 0; if (dday >= 0 && dday < 6) { curDay = 0; } else if (dday >= 6 && dday < 12) { curDay = 1; } else if (dday >= 12 && dday < 18) { curDay = 2; } else if (dday >= 18 && dday < 24) { curDay = 3; } else if (dday >= 24 && dday < 30) { curDay = 4; } else { curDay = 5; } days[curDay].matrix[index2] = true; days[curDay].matrixL[index2] = freeLesson; } //проводим оценку начальной особи по хромосомам Rating ratio = new Rating(days, maxStack, unicLessons); //заносим начальную популяцию в generations Generations generic = new Generations("популяция #0"); generic.mark = ratio.TotalMark();//считаем общую оценку особи generic.days = ratio.InputMarksAndDays(); generations.Add(new Generations(generic)); firstmark = generic.mark; generic = null; //generator = new Generator(days, maxStack, unicLessons, generations, firstmark);//вносим первую основную особь в генератор }
public void GetPopulations(int NumGenerations, int stop) { bool block = false;//блокировка ограничений на количество итераций, по умолчанию блок выключен int count = 0; if (stop > 0) { block = true; count = 0;//счетчик } //---------объявления------------- Day[] mainPerson = new Day[6]; // основная особь, в начале необходимо скопировать в неё экземпляр из первого поколения double mainMark; // оценка основной особи, с которой происходит сравнение при отборе //---------присваивания------------- for (int i = 0; i < 6; i++) { mainPerson[i] = new Day(main.days[i]); } mainMark = main.firstmark; unicLessons = main.unicLessons; generations = main.generations; //вырастим numPopulations поколений for (int j = 0; j < NumGenerations; j++) { List <Day[]> population = new List <Day[]>();//популяция из нескольких особей string[] names = new string[15]; double[] marks = new double[15]; //возьмем основную особь и составим 15 вариантов её скрещивания по заранее составленной схеме for (int i = 0; i < 15; i++) { Day[] person = new Day[6]; for (int k = 0; k < 6; k++) { person[k] = new Day(); } person = GetNewGeneration(mainPerson, i); Rating ratio = new Rating(person, main.maxStack, unicLessons); names[i] = "популяция #" + (j + 1) + " особь под номером #" + ((j * 15) + (i + 1)); marks[i] = ratio.TotalMark();//считаем общую оценку особи person = ratio.InputMarksAndDays(); population.Add(person); } int index = -1; for (int i = 0; i < 15; i++) { if (mainMark > marks[i]) { mainMark = marks[i]; index = i; } } if (index != -1)//если родительская особь лучше своих поколений, то все поколение бракуется | иначе назначается новая особь, а результат добавляется в список поколений { if (block) { count = 0; //обнуление счетчика } for (int i = 0; i < 6; i++) { mainPerson[i] = new Day(population[index][i]); } Generations generic = new Generations(names[index]); generic.mark = mainMark; generic.Input(mainPerson); generations.Add(new Generations(generic));//добавляем новую особь в список } if (block) { count++; if (count == stop) { j = NumGenerations; //если в течение <stop> не было улучшений, то выходим из цикла } } } }