Exemplo n.º 1
0
int main(int argc, char *argv[]) {

	startRobogen();

	// ---------------------------------------
	// verify usage and load configuration
	// ---------------------------------------
	if (argc > 1 && std::string(argv[1]) == "--help") {
		printUsage(argv);
		printHelp();
		exitRobogen(EXIT_SUCCESS);
	}

	if ((argc < 4)) {
		printUsage(argv);
		std::cout << "RUN: " << std::endl << std::endl
				<< "      " << std::string(argv[0])
				<< " --help to see all configuration options."
				<< std::endl << std::endl;
		exitRobogen(EXIT_FAILURE);
	}


	unsigned int seed = atoi(argv[1]);
	std::string outputDirectory = std::string(argv[2]);
	std::string confFileName = std::string(argv[3]);

	bool overwrite = false;
	bool saveAll = false;
	int currentArg = 4;
	for (; currentArg<argc; currentArg++) {
		if (std::string("--help").compare(argv[currentArg]) == 0) {
			printUsage(argv);
			printHelp();
			return EXIT_SUCCESS;
		} else if (std::string("--overwrite").compare(argv[currentArg]) == 0) {
			overwrite = true;
		} else if (std::string("--save-all").compare(argv[currentArg]) == 0) {
			saveAll = true;
		} else {
			std::cerr << std::endl << "Invalid option: " << argv[currentArg]
							 << std::endl << std::endl;
			printUsage(argv);
			exitRobogen(EXIT_FAILURE);
		}


	}


	// Create random number generator
	boost::random::mt19937 rng;
	rng.seed(seed);

	boost::shared_ptr<EvolverConfiguration> conf =
			boost::shared_ptr<EvolverConfiguration>(new EvolverConfiguration());
	if (!conf->init(confFileName)) {
		std::cerr << "Problems parsing the evolution configuration file. Quit."
				<< std::endl;
		exitRobogen(EXIT_FAILURE);
	}

	boost::shared_ptr<RobogenConfig> robotConf =
			ConfigurationReader::parseConfigurationFile(
					conf->simulatorConfFile);
	if (robotConf == NULL) {
		std::cerr << "Problems parsing the robot configuration file. Quit."
				<< std::endl;
		exitRobogen(EXIT_FAILURE);
	}

	// ---------------------------------------
	// Set up evolution
	// ---------------------------------------

	boost::shared_ptr<Selector> selector;
	if (conf->selection == conf->DETERMINISTIC_TOURNAMENT) {
		selector.reset(new DeterministicTournament(conf->tournamentSize, rng));
	} else {
		std::cerr << "Selection type id " << conf->selection << " unknown."
				<< std::endl;
		exitRobogen(EXIT_FAILURE);
	}
	boost::shared_ptr<Mutator> mutator = boost::shared_ptr<Mutator>(
			new Mutator(conf, rng));
	boost::shared_ptr<EvolverLog> log(new EvolverLog());
	if (!log->init(conf, robotConf, outputDirectory, overwrite, saveAll)) {
		std::cout << "Error creating evolver log. Aborting." << std::endl;
		return EXIT_FAILURE;
	}

	// ---------------------------------------
	// parse robot from file & initialize population
	// ---------------------------------------

	boost::shared_ptr<RobotRepresentation> referenceBot(
			new RobotRepresentation());
	bool growBodies = false;
	if (conf->evolutionMode == EvolverConfiguration::BRAIN_EVOLVER
			&& conf->referenceRobotFile.compare("") == 0) {
		std::cerr << "Trying to evolve brain, but no robot file provided."
				<< std::endl;
		exitRobogen(EXIT_FAILURE);
	} else if (conf->referenceRobotFile.compare("") != 0) {
		if (!referenceBot->init(conf->referenceRobotFile)) {
			std::cerr << "Failed interpreting robot from text file"
					<< std::endl;
			exitRobogen(EXIT_FAILURE);
		}
	} else { //doing body evolution and don't have a reference robot
		if (referenceBot->init()) {
			growBodies = true;
		} else {
			std::cerr << "Failed creating base robot for body evolution"
					<< std::endl;
			exitRobogen(EXIT_FAILURE);
		}
	}
	

	boost::shared_ptr<Population> population(new Population());
	boost::shared_ptr<NeatContainer> neatContainer;

	bool neat = (conf->evolutionaryAlgorithm ==
			EvolverConfiguration::HYPER_NEAT);

	if (!population->init(referenceBot, conf->mu, mutator, growBodies,
			(!(conf->useBrainSeed || neat)) ) ) {
		std::cerr << "Error when initializing population!" << std::endl;
		exitRobogen(EXIT_FAILURE);
	}

	if (neat) {
		neatContainer.reset(new NeatContainer(conf, population, seed, rng));

	}




	// ---------------------------------------
	// open sockets for communication with simulator processes
	// ---------------------------------------

	std::vector<TcpSocket*> sockets(conf->sockets.size());
	for (unsigned int i = 0; i < conf->sockets.size(); i++) {
		sockets[i] = new TcpSocket;
#ifndef FAKEROBOTREPRESENTATION_H // do not bother with sockets when using
		// benchmark
		if (!sockets[i]->open(conf->sockets[i].first,
				conf->sockets[i].second)) {
			std::cerr << "Could not open connection to simulator" << std::endl;
			exitRobogen(EXIT_FAILURE);
		}
#endif
	}

	// ---------------------------------------
	// run evolution TODO stopping criterion
	// ---------------------------------------

	if(neat) {
		if(!neatContainer->fillPopulationWeights(population)) {
			std::cerr << "Filling weights from NEAT failed." << std::endl;
			exitRobogen(EXIT_FAILURE);
		}
	}

	population->evaluate(robotConf, sockets);
	if (!log->logGeneration(1, *population.get())) {
		exitRobogen(EXIT_FAILURE);
	}

	for (unsigned int generation = 2; generation <= conf->numGenerations;
			++generation) {
		// create children
		IndividualContainer children;
		if (neat) {
			//neatPopulation->Epoch();
			if(!neatContainer->produceNextGeneration(population)) {
				std::cerr << "Producing next generation from NEAT failed."
						<< std::endl;
				exitRobogen(EXIT_FAILURE);
			}
			population->evaluate(robotConf, sockets);
			population->sort(true);
		} else {
			selector->initPopulation(population);
			for (unsigned int i = 0; i < conf->lambda; i++) {
				std::pair<boost::shared_ptr<RobotRepresentation>,
						boost::shared_ptr<RobotRepresentation> > selection;
				if (!selector->select(selection)) {
					std::cerr << "Selector::select() failed." << std::endl;
					exitRobogen(EXIT_FAILURE);
				}
				children.push_back(
						mutator->mutate(selection.first, selection.second));
			}

			// evaluate children
			children.evaluate(robotConf, sockets);

			// comma or plus?
			if (conf->replacement == conf->PLUS_REPLACEMENT) {
				children += *population.get();
			}

			// replace
			population.reset(new Population());
			if (!population->init(children, conf->mu)) {
				std::cerr << "Error when initializing population!" << std::endl;
				exitRobogen(EXIT_FAILURE);
			}
		}


		if (!log->logGeneration(generation, *population.get())) {
			exitRobogen(EXIT_FAILURE);
		}
	}

	// Clean up sockets
	for (unsigned int i = 0; i < conf->sockets.size(); i++) {
		delete sockets[i];
	}

	exitRobogen(EXIT_SUCCESS);
}
Exemplo n.º 2
0
void mainEvolutionLoop() {
#ifdef EMSCRIPTEN
	std::stringstream ss;
	double best, average, stddev;
	population->getStat(best, average, stddev);
	ss << "{best : " << best << ", average : " << average << ", stddev : "
			<< stddev << ", generation : " << generation << "}";
	sendJSEvent("stats", ss.str());
#endif

	std::cout << "mainEvolutionLoop" << std::endl;
	if (!log->logGeneration(generation, *population.get())) {
		exitRobogen(EXIT_FAILURE);
	}

	generation++;


	if (generation <= conf->numGenerations) {
		std::cout << "Generation " << generation << std::endl;
		children.clear();

		// create children
		if (neat) {
			//neatPopulation->Epoch();
			if(!neatContainer->produceNextGeneration(population)) {
				std::cerr << "Producing next generation from NEAT failed."
						<< std::endl;
				exitRobogen(EXIT_FAILURE);
			}
			population->evaluate(robotConf, sockets);

		} else {
			selector->initPopulation(population);
			unsigned int numOffspring = 0;
			while (numOffspring < conf->lambda) {

				std::pair<boost::shared_ptr<RobotRepresentation>,
						boost::shared_ptr<RobotRepresentation> > selection;
				if (!selector->select(selection.first)) {
					std::cerr << "Selector::select() failed." << std::endl;
					exitRobogen(EXIT_FAILURE);
				}
				unsigned int tries = 0;
				do {
					if (tries > 10000) {
						std::cerr << "Selecting second parent failed after "
								"10000 tries, giving up.";
						exitRobogen(EXIT_FAILURE);
					}
					if (!selector->select(selection.second)) {
						std::cerr << "Selector::select() failed." << std::endl;
						exitRobogen(EXIT_FAILURE);
					}
					tries++;
				} while (selection.first == selection.second);

				std::vector<boost::shared_ptr<RobotRepresentation> > offspring
					= mutator->createOffspring(selection.first,
											   selection.second);

				// no crossover, or can fit both new individuals
				if ( (numOffspring + offspring.size()) <= conf->lambda ) {
					children.insert(children.end(), offspring.begin(),
													offspring.end() );
					numOffspring += offspring.size();
				} else { // crossover, but can only fit one
					children.push_back(offspring[0]);
					numOffspring++;
				}
			}
			children.evaluate(robotConf, sockets);
		}
#ifndef EMSCRIPTEN
		triggerPostEvaluate();
#endif
	} else {
#ifdef EMSCRIPTEN
		sendJSEvent("evolutionTerminated", "{}");
#endif

	}
}