Commit 58336c12 authored by Romain Reuillon's avatar Romain Reuillon
Browse files

[Lib] update mgo

parent c87d099e
Pipeline #363 passed with stage
in 19 minutes and 41 seconds
......@@ -217,7 +217,7 @@ lazy val cats =
version := catsVersion
) settings(settings: _*)
lazy val squantsVersion = "1.3.0"
lazy val squantsVersion = "1.4.0"
lazy val squants =
OsgiProject(dir, "squants") settings (
......@@ -226,7 +226,7 @@ lazy val squants =
) settings(settings: _*)
lazy val mgoVersion = "3.29"
lazy val mgoVersion = "3.30"
lazy val mgo = OsgiProject(dir, "mgo", exports = Seq("mgo.*", "freestyle.*"), imports = Seq("!better.*", "!javax.xml.*", "!scala.meta.*", "!sun.misc.*", "*"), privatePackages = Seq("!scala.*", "!monocle.*", "!org.apache.commons.math3.*", "!cats.*", "!squants.*", "!scalaz.*", "*")) settings(
libraryDependencies += "fr.iscpif" %% "mgo" % mgoVersion,
......
......@@ -50,9 +50,9 @@ object NSGA2 {
import cats.data._
import mgo.evolution.contexts._
implicit def integration: MGOAPI.Integration[DeterministicParams, (Vector[Double], Vector[Int]), Vector[Double]] = new MGOAPI.Integration[DeterministicParams, (Vector[Double], Vector[Int]), Vector[Double]] {
implicit def integration: MGOAPI.Integration[DeterministicParams, (Vector[Double], Vector[Int]), Array[Any]] = new MGOAPI.Integration[DeterministicParams, (Vector[Double], Vector[Int]), Array[Any]] {
type G = CDGenome.Genome
type I = CDGenome.DeterministicIndividual.Individual
type I = CDGenome.DeterministicIndividual.Individual[Array[Any]]
type S = EvolutionState[Unit]
def iManifest = implicitly
......@@ -81,13 +81,13 @@ object NSGA2 {
def buildGenome(v: (Vector[Double], Vector[Int])): G = CDGenome.buildGenome(v._1, None, v._2, None)
def buildGenome(vs: Vector[Variable[_]]) = Genome.fromVariables(vs, om.genome).map(buildGenome)
def buildIndividual(genome: G, phenotype: Vector[Double], context: Context) = CDGenome.DeterministicIndividual.buildIndividual(genome, phenotype)
def buildIndividual(genome: G, phenotype: Array[Any], context: Context) = CDGenome.DeterministicIndividual.buildIndividual(genome, phenotype)
def initialState(rng: util.Random) = EvolutionState[Unit](random = rng, s = ())
def result(population: Vector[I], state: S) = FromContext { p
import p._
val res = MGONSGA2.result(population, Genome.continuous(om.genome).from(context))
val res = MGONSGA2.result[Array[Any]](population, Genome.continuous(om.genome).from(context), ExactObjective.toFitnessFunction(om.objectives))
val genomes = GAIntegration.genomesOfPopulationToVariables(om.genome, res.map(_.continuous) zip res.map(_.discrete), scale = false).from(context)
val fitness = GAIntegration.objectivesOfPopulationToVariables(om.objectives, res.map(_.fitness)).from(context)
......@@ -108,7 +108,7 @@ object NSGA2 {
Genome.discrete(om.genome).map { discrete
interpret { impl
import impl._
zipWithState(MGONSGA2.adaptiveBreeding[DSL](n, om.operatorExploration, discrete).run(individuals)).eval
zipWithState(MGONSGA2.adaptiveBreeding[DSL, Array[Any]](n, om.operatorExploration, discrete, ExactObjective.toFitnessFunction(om.objectives)).run(individuals)).eval
}
}
......@@ -118,7 +118,7 @@ object NSGA2 {
import impl._
def step =
for {
elited MGONSGA2.elitism[DSL](om.mu, continuous) apply (population, candidates)
elited MGONSGA2.elitism[DSL, Array[Any]](om.mu, continuous, ExactObjective.toFitnessFunction(om.objectives)) apply (population, candidates)
_ mgo.evolution.elitism.incrementGeneration[DSL]
} yield elited
......@@ -245,7 +245,7 @@ object NSGA2 {
}
NoisyObjective
def migrateToIsland(population: Vector[I]) = StochasticGAIntegration.migrateToIsland[I](population, CDGenome.NoisyIndividual.Individual.historyAge)
def migrateFromIsland(population: Vector[I], state: S) = StochasticGAIntegration.migrateFromIsland[I, Array[Any]](population, CDGenome.NoisyIndividual.Individual.historyAge, CDGenome.NoisyIndividual.Individual.fitnessHistory)
def migrateFromIsland(population: Vector[I], state: S) = StochasticGAIntegration.migrateFromIsland[I, Array[Any]](population, CDGenome.NoisyIndividual.Individual.historyAge, CDGenome.NoisyIndividual.Individual.phenotypeHistory[Array[Any]])
}
}
......
......@@ -30,40 +30,40 @@ object NichedNSGA2Algorithm {
case class Result[N](continuous: Vector[Double], discrete: Vector[Int], fitness: Vector[Double], niche: N)
def result[N](population: Vector[Individual], niche: Individual N, continuous: Vector[C]) = {
nicheElitism[Id, Individual, N](population, keepFirstFront(_, vectorFitness.get), niche).map { i
def result[N, P](population: Vector[Individual[P]], niche: Individual[P] N, continuous: Vector[C], fitness: P Vector[Double]) = {
nicheElitism[Id, Individual[P], N](population, keepFirstFront[Individual[P]](_, i fitness(i.phenotype)), niche).map { i
Result(
scaleContinuousValues(continuousValues.get(i.genome), continuous),
Individual.genome composeLens discreteValues get i,
i.fitness.toVector,
fitness(i.phenotype),
niche(i))
}
}
def continuousProfile(x: Int, nX: Int): Niche[Individual, Int] =
mgo.evolution.niche.continuousProfile[Individual]((Individual.genome composeLens continuousValues).get _, x, nX)
def continuousProfile[P](x: Int, nX: Int): Niche[Individual[P], Int] =
mgo.evolution.niche.continuousProfile[Individual[P]]((Individual.genome composeLens continuousValues).get _, x, nX)
def discreteProfile(x: Int): Niche[Individual, Int] =
mgo.evolution.niche.discreteProfile[Individual]((Individual.genome composeLens discreteValues).get _, x)
def discreteProfile[P](x: Int): Niche[Individual[P], Int] =
mgo.evolution.niche.discreteProfile[Individual[P]]((Individual.genome composeLens discreteValues).get _, x)
def boundedContinuousProfile(continuous: Vector[C], x: Int, nX: Int, min: Double, max: Double): Niche[Individual, Int] =
mgo.evolution.niche.boundedContinuousProfile[Individual](i scaleContinuousValues(continuousValues.get(i.genome), continuous), x, nX, min, max)
def boundedContinuousProfile[P](continuous: Vector[C], x: Int, nX: Int, min: Double, max: Double): Niche[Individual[P], Int] =
mgo.evolution.niche.boundedContinuousProfile[Individual[P]](i scaleContinuousValues(continuousValues.get(i.genome), continuous), x, nX, min, max)
def gridContinuousProfile(continuous: Vector[C], x: Int, intervals: Vector[Double]): Niche[Individual, Int] =
mgo.evolution.niche.gridContinuousProfile[Individual](i scaleContinuousValues(continuousValues.get(i.genome), continuous), x, intervals)
def gridContinuousProfile[P](continuous: Vector[C], x: Int, intervals: Vector[Double]): Niche[Individual[P], Int] =
mgo.evolution.niche.gridContinuousProfile[Individual[P]](i scaleContinuousValues(continuousValues.get(i.genome), continuous), x, intervals)
def boundedObjectiveProfile(x: Int, nX: Int, min: Double, max: Double): Niche[Individual, Int] =
mgo.evolution.niche.boundedContinuousProfile[Individual](vectorFitness.get _, x, nX, min, max)
def boundedObjectiveProfile[P](x: Int, nX: Int, min: Double, max: Double, fitness: P Vector[Double]): Niche[Individual[P], Int] =
mgo.evolution.niche.boundedContinuousProfile[Individual[P]](i fitness(i.phenotype), x, nX, min, max)
def gridObjectiveProfile(x: Int, intervals: Vector[Double]): Niche[Individual, Int] =
mgo.evolution.niche.gridContinuousProfile[Individual](vectorFitness.get _, x, intervals)
def gridObjectiveProfile[P](x: Int, intervals: Vector[Double], fitness: P Vector[Double]): Niche[Individual[P], Int] =
mgo.evolution.niche.gridContinuousProfile[Individual[P]](i fitness(i.phenotype), x, intervals)
def initialGenomes[M[_]: cats.Monad: Random](lambda: Int, continuous: Vector[C], discrete: Vector[D]) =
CDGenome.initialGenomes[M](lambda, continuous, discrete)
def adaptiveBreeding[M[_]: Generation: Random: cats.Monad](lambda: Int, operatorExploration: Double, discrete: Vector[D]): Breeding[M, Individual, Genome] =
NSGA2Operations.adaptiveBreeding[M, Individual, Genome](
vectorFitness.get,
def adaptiveBreeding[M[_]: Generation: Random: cats.Monad, P](lambda: Int, operatorExploration: Double, discrete: Vector[D], fitness: P Vector[Double]): Breeding[M, Individual[P], Genome] =
NSGA2Operations.adaptiveBreeding[M, Individual[P], Genome](
i fitness(i.phenotype),
Individual.genome.get,
continuousValues.get,
continuousOperator.get,
......@@ -75,12 +75,12 @@ object NichedNSGA2Algorithm {
lambda,
operatorExploration)
def expression(fitness: (Vector[Double], Vector[Int]) Vector[Double], components: Vector[C]): Genome Individual =
DeterministicIndividual.expression(fitness, components)
def expression[P](fitness: (Vector[Double], Vector[Int]) P, components: Vector[C]): Genome Individual[P] =
DeterministicIndividual.expression[P](fitness, components)
def elitism[M[_]: cats.Monad: Random: Generation, N](niche: Niche[Individual, N], mu: Int, components: Vector[C]): Elitism[M, Individual] =
ProfileOperations.elitism[M, Individual, N](
vectorFitness.get,
def elitism[M[_]: cats.Monad: Random: Generation, N, P](niche: Niche[Individual[P], N], mu: Int, components: Vector[C], fitness: P Vector[Double]): Elitism[M, Individual[P]] =
ProfileOperations.elitism[M, Individual[P], N](
i fitness(i.phenotype),
i values(Individual.genome.get(i), components),
niche,
mu)
......@@ -112,9 +112,9 @@ object NoisyNichedNSGA2Algorithm {
if (population.isEmpty) population
else if (onlyOldest) {
val firstFront = keepFirstFront(population, NoisyNSGA2.fitness[P](aggregation))
val sorted = firstFront.sortBy(-_.fitnessHistory.size)
val maxHistory = sorted.head.fitnessHistory.size
firstFront.filter(_.fitnessHistory.size == maxHistory)
val sorted = firstFront.sortBy(-_.phenotypeHistory.size)
val maxHistory = sorted.head.phenotypeHistory.size
firstFront.filter(_.phenotypeHistory.size == maxHistory)
}
else keepFirstFront(population, NoisyNSGA2.fitness[P](aggregation))
......@@ -162,7 +162,7 @@ object NoisyNichedNSGA2Algorithm {
NoisyProfileOperations.elitism[M, Individual[P], N, P](
aggregatedFitness(aggregation),
mergeHistories(individualValues, vectorFitness, Individual.historyAge, historySize),
mergeHistories(individualValues, vectorPhenotype, Individual.historyAge, historySize),
individualValues,
niche,
muByNiche)
......@@ -200,7 +200,7 @@ object NichedNSGA2 {
object DeterministicParams {
def niche(genome: Genome, objectives: Objectives, profiled: Seq[NichedElement]) = {
def niche(genome: Genome, objectives: Seq[ExactObjective[_]], profiled: Seq[NichedElement]) = {
def notFoundInGenome(v: Val[_]) = throw new UserBadDataError(s"Variable $v not found in the genome")
......@@ -208,37 +208,37 @@ object NichedNSGA2 {
profiled.toVector.map {
case c: NichedElement.Continuous
val index = Genome.continuousIndex(genome, c.v).getOrElse(notFoundInGenome(c.v))
NichedNSGA2Algorithm.continuousProfile(index, c.n).pure[FromContext]
NichedNSGA2Algorithm.continuousProfile[Array[Any]](index, c.n).pure[FromContext]
case c: NichedElement.ContinuousSequence
val index = Genome.continuousIndex(genome, c.v).getOrElse(notFoundInGenome(c.v))
NichedNSGA2Algorithm.continuousProfile(index + c.i, c.n).pure[FromContext]
NichedNSGA2Algorithm.continuousProfile[Array[Any]](index + c.i, c.n).pure[FromContext]
case c: NichedElement.Discrete
val index = Genome.discreteIndex(genome, c.v).getOrElse(notFoundInGenome(c.v))
NichedNSGA2Algorithm.discreteProfile(index).pure[FromContext]
NichedNSGA2Algorithm.discreteProfile[Array[Any]](index).pure[FromContext]
case c: NichedElement.DiscreteSequence
val index = Genome.discreteIndex(genome, c.v).getOrElse(notFoundInGenome(c.v))
NichedNSGA2Algorithm.discreteProfile(index + c.i).pure[FromContext]
NichedNSGA2Algorithm.discreteProfile[Array[Any]](index + c.i).pure[FromContext]
case c: NichedElement.GridContinuous FromContext { p
import p._
(Genome.continuousIndex(genome, c.v), Objective.index(objectives, c.v)) match {
case (Some(index), _) NichedNSGA2Algorithm.gridContinuousProfile(Genome.continuous(genome).from(context), index, c.intervals)
case (_, Some(index)) NichedNSGA2Algorithm.gridObjectiveProfile(index, c.intervals)
case (Some(index), _) NichedNSGA2Algorithm.gridContinuousProfile[Array[Any]](Genome.continuous(genome).from(context), index, c.intervals)
case (_, Some(index)) NichedNSGA2Algorithm.gridObjectiveProfile[Array[Any]](index, c.intervals, ExactObjective.toFitnessFunction(objectives))
case _ throw new UserBadDataError(s"Variable ${c.v} not found neither in the genome nor in the objectives")
}
}
}.sequence
niches.map { ns mgo.evolution.niche.sequenceNiches[CDGenome.DeterministicIndividual.Individual, Int](ns) }
niches.map { ns mgo.evolution.niche.sequenceNiches[CDGenome.DeterministicIndividual.Individual[Array[Any]], Int](ns) }
}
import CDGenome.DeterministicIndividual
import cats.data._
import mgo.evolution.contexts._
implicit def integration = new MGOAPI.Integration[DeterministicParams, (Vector[Double], Vector[Int]), Vector[Double]] {
implicit def integration = new MGOAPI.Integration[DeterministicParams, (Vector[Double], Vector[Int]), Array[Any]] {
type G = CDGenome.Genome
type I = DeterministicIndividual.Individual
type I = DeterministicIndividual.Individual[Array[Any]]
type S = EvolutionState[Unit]
def iManifest = implicitly
......@@ -266,13 +266,13 @@ object NichedNSGA2 {
def buildGenome(v: (Vector[Double], Vector[Int])): G = CDGenome.buildGenome(v._1, None, v._2, None)
def buildGenome(vs: Vector[Variable[_]]) = Genome.fromVariables(vs, om.genome).map(buildGenome)
def buildIndividual(genome: G, phenotype: Vector[Double], context: Context) = CDGenome.DeterministicIndividual.buildIndividual(genome, phenotype)
def buildIndividual(genome: G, phenotype: Array[Any], context: Context) = CDGenome.DeterministicIndividual.buildIndividual(genome, phenotype)
def initialState(rng: util.Random) = EvolutionState[Unit](random = rng, s = ())
def result(population: Vector[I], state: S) = FromContext { p
import p._
val res = NichedNSGA2Algorithm.result(population, om.niche.from(context), Genome.continuous(om.genome).from(context))
val res = NichedNSGA2Algorithm.result(population, om.niche.from(context), Genome.continuous(om.genome).from(context), ExactObjective.toFitnessFunction(om.objectives))
val genomes = GAIntegration.genomesOfPopulationToVariables(om.genome, res.map(_.continuous) zip res.map(_.discrete), scale = false).from(context)
val fitness = GAIntegration.objectivesOfPopulationToVariables(om.objectives, res.map(_.fitness)).from(context)
......@@ -291,7 +291,7 @@ object NichedNSGA2 {
Genome.discrete(om.genome).map { discrete
interpret { impl
import impl._
zipWithState(mgo.evolution.algorithm.Profile.adaptiveBreeding[DSL](n, om.operatorExploration, discrete).run(population)).eval
zipWithState(mgo.evolution.algorithm.Profile.adaptiveBreeding[DSL, Array[Any]](n, om.operatorExploration, discrete, ExactObjective.toFitnessFunction(om.objectives)).run(population)).eval
}
}
......@@ -301,7 +301,7 @@ object NichedNSGA2 {
import impl._
def step =
for {
elited NichedNSGA2Algorithm.elitism[DSL, Vector[Int]](om.niche.from(context), om.nicheSize, Genome.continuous(om.genome).from(context)) apply (population, candidates)
elited NichedNSGA2Algorithm.elitism[DSL, Vector[Int], Array[Any]](om.niche.from(context), om.nicheSize, Genome.continuous(om.genome).from(context), ExactObjective.toFitnessFunction((om.objectives))) apply (population, candidates)
_ mgo.evolution.elitism.incrementGeneration[DSL]
} yield elited
......@@ -328,7 +328,7 @@ object NichedNSGA2 {
case class DeterministicParams(
nicheSize: Int,
niche: FromContext[Niche[CDGenome.DeterministicIndividual.Individual, Vector[Int]]],
niche: FromContext[Niche[CDGenome.DeterministicIndividual.Individual[Array[Any]], Vector[Int]]],
genome: Genome,
objectives: Seq[ExactObjective[_]],
operatorExploration: Double)
......@@ -459,7 +459,7 @@ object NichedNSGA2 {
}
def migrateToIsland(population: Vector[I]) = StochasticGAIntegration.migrateToIsland[I](population, CDGenome.NoisyIndividual.Individual.historyAge)
def migrateFromIsland(population: Vector[I], state: S) = StochasticGAIntegration.migrateFromIsland[I, Array[Any]](population, CDGenome.NoisyIndividual.Individual.historyAge, CDGenome.NoisyIndividual.Individual.fitnessHistory)
def migrateFromIsland(population: Vector[I], state: S) = StochasticGAIntegration.migrateFromIsland[I, Array[Any]](population, CDGenome.NoisyIndividual.Individual.historyAge, CDGenome.NoisyIndividual.Individual.phenotypeHistory)
}
}
......@@ -488,7 +488,7 @@ object NichedNSGA2 {
DeterministicParams(
genome = genome,
objectives = exactObjectives,
niche = DeterministicParams.niche(genome, objectives, niche),
niche = DeterministicParams.niche(genome, exactObjectives, niche),
operatorExploration = operatorExploration,
nicheSize = nicheSize
),
......
......@@ -23,7 +23,7 @@ object OSE {
origin: (Vector[Double], Vector[Int]) Vector[Int],
limit: Vector[Double],
genome: Genome,
objectives: Objectives,
objectives: Seq[ExactObjective[_]],
operatorExploration: Double)
object DeterministicParams {
......@@ -33,16 +33,16 @@ object OSE {
import mgo.evolution.algorithm.{ OSE MGOOSE, _ }
import mgo.evolution.contexts._
implicit def integration = new MGOAPI.Integration[DeterministicParams, (Vector[Double], Vector[Int]), Vector[Double]] { api
implicit def integration = new MGOAPI.Integration[DeterministicParams, (Vector[Double], Vector[Int]), Array[Any]] { api
type G = CDGenome.Genome
type I = CDGenome.DeterministicIndividual.Individual
type S = EvolutionState[OSEState]
type I = CDGenome.DeterministicIndividual.Individual[Array[Any]]
type S = EvolutionState[OSEState[Array[Any]]]
def iManifest = implicitly
def gManifest = implicitly
def sManifest = implicitly
private def interpret[U](f: MGOOSE.OSEImplicits (S, U)) = State[S, U] { (s: S)
private def interpret[U](f: MGOOSE.OSEImplicits[Array[Any]] (S, U)) = State[S, U] { (s: S)
MGOOSE.run(s)(f)
}
......@@ -50,7 +50,7 @@ object OSE {
import cats.implicits._
for {
t op
newState MGOOSE.state[M]
newState MGOOSE.state[M, Array[Any]]
} yield (newState, t)
}
......@@ -76,9 +76,9 @@ object OSE {
def buildGenome(v: (Vector[Double], Vector[Int])): G = CDGenome.buildGenome(v._1, None, v._2, None)
def buildGenome(vs: Vector[Variable[_]]) = Genome.fromVariables(vs, om.genome).map(buildGenome)
def buildIndividual(genome: G, phenotype: Vector[Double], context: Context) = CDGenome.DeterministicIndividual.buildIndividual(genome, phenotype)
def buildIndividual(genome: G, phenotype: Array[Any], context: Context) = CDGenome.DeterministicIndividual.buildIndividual(genome, phenotype)
def initialState(rng: util.Random) = EvolutionState[OSEState](random = rng, s = (Array.empty, Array.empty))
def initialState(rng: util.Random) = EvolutionState[OSEState[Array[Any]]](random = rng, s = (Array.empty, Array.empty))
def afterGeneration(g: Long, population: Vector[I]) = api.afterGeneration(g, population)
def afterDuration(d: squants.Time, population: Vector[I]) = api.afterDuration(d, population)
......@@ -86,7 +86,7 @@ object OSE {
def result(population: Vector[I], state: S) = FromContext { p
import p._
val res = MGOOSE.result(state, Genome.continuous(om.genome).from(context))
val res = MGOOSE.result[Array[Any]](state, Genome.continuous(om.genome).from(context), ExactObjective.toFitnessFunction(om.objectives))
val genomes = GAIntegration.genomesOfPopulationToVariables(om.genome, res.map(_.continuous) zip res.map(_.discrete), scale = false).from(context)
val fitness = GAIntegration.objectivesOfPopulationToVariables(om.objectives, res.map(_.fitness)).from(context)
......@@ -110,11 +110,12 @@ object OSE {
import mgo.tagtools._
import impl._
zipWithState(
MGOOSE.adaptiveBreeding[mgo.tagtools.DSL](
MGOOSE.adaptiveBreeding[mgo.tagtools.DSL, Array[Any]](
n,
om.operatorExploration,
discrete,
om.origin).run(individuals)).eval
om.origin,
ExactObjective.toFitnessFunction(om.objectives)).run(individuals)).eval
}
}
......@@ -125,7 +126,7 @@ object OSE {
import impl._
def step =
for {
elited MGOOSE.elitism[mgo.tagtools.DSL](om.mu, om.limit, om.origin, continuous) apply (population, candidates)
elited MGOOSE.elitism[mgo.tagtools.DSL, Array[Any]](om.mu, om.limit, om.origin, continuous, ExactObjective.toFitnessFunction(om.objectives)) apply (population, candidates)
_ mgo.evolution.elitism.incrementGeneration[mgo.tagtools.DSL]
} yield elited
......@@ -264,7 +265,7 @@ object OSE {
def afterDuration(d: squants.Time, population: Vector[I]) = api.afterDuration(d, population)
def migrateToIsland(population: Vector[I]) = StochasticGAIntegration.migrateToIsland[I](population, CDGenome.NoisyIndividual.Individual.historyAge)
def migrateFromIsland(population: Vector[I], state: S) = StochasticGAIntegration.migrateFromIsland[I, Array[Any]](population ++ state.s._1, CDGenome.NoisyIndividual.Individual.historyAge, CDGenome.NoisyIndividual.Individual.fitnessHistory)
def migrateFromIsland(population: Vector[I], state: S) = StochasticGAIntegration.migrateFromIsland[I, Array[Any]](population ++ state.s._1, CDGenome.NoisyIndividual.Individual.historyAge, CDGenome.NoisyIndividual.Individual.phenotypeHistory[Array[Any]])
}
......
......@@ -71,12 +71,6 @@ object Objective {
case x Some(x)
}
def toDouble[P](o: ExactObjective[P], context: Context) = {
def value = o.toDouble(o.get(context))
def deltaValue = o.delta.map(d math.abs(value - d)).getOrElse(value)
if (!o.negative) deltaValue else -deltaValue
}
def prototype(o: Objective[_]) =
o match {
case e: ExactObjective[_] e.prototype
......@@ -103,7 +97,25 @@ object Objective {
}
sealed trait Objective[P]
case class ExactObjective[P](prototype: Val[P], get: Context P, toDouble: P Double, negative: Boolean, delta: Option[Double]) extends Objective[P]
object ExactObjective {
def toDouble[P](o: ExactObjective[P], context: Context) = {
def value = o.toDouble(o.get(context))
def deltaValue = o.delta.map(d math.abs(value - d)).getOrElse(value)
if (!o.negative) deltaValue else -deltaValue
}
def toFitnessFunction(objectives: Seq[ExactObjective[_]])(phenotype: Array[Any]) =
for {
(o, p) (objectives zip phenotype).toVector
} yield o.fromAny(p)
}
case class ExactObjective[P](prototype: Val[P], get: Context P, toDouble: P Double, negative: Boolean, delta: Option[Double]) extends Objective[P] {
def fromAny(v: Any) = toDouble(v.asInstanceOf[P])
}
object NoisyObjective {
......
......@@ -58,20 +58,20 @@ object PSEAlgorithm {
import GenomeVectorDouble._
import CDGenome._
@Lenses case class Individual(
@Lenses case class Individual[P](
genome: Genome,
phenotype: Array[Double],
foundedIsland: Boolean = false)
phenotype: P,
foundedIsland: Boolean = false)
case class Result(continuous: Vector[Double], discrete: Vector[Int], pattern: Vector[Int], phenotype: Vector[Double])
def result(population: Vector[Individual], continuous: Vector[C], pattern: Vector[Double] Vector[Int]) =
def result[P](population: Vector[Individual[P]], continuous: Vector[C], pattern: Vector[Double] Vector[Int], phenotype: P Vector[Double]) =
population.map { i
Result(
scaleContinuousValues(continuousValues.get(i.genome), continuous),
Individual.genome composeLens discreteValues get i,
pattern(i.phenotype.toVector),
i.phenotype.toVector)
pattern(phenotype(i.phenotype)),
phenotype(i.phenotype))
}
def state[M[_]: cats.Monad: StartTime: Random: Generation](implicit hitmap: HitMap[M]) = for {
......@@ -79,37 +79,37 @@ object PSEAlgorithm {
s mgo.evolution.algorithm.state[M, Map[Vector[Int], Int]](map)
} yield s
def buildIndividual(g: Genome, f: Vector[Double]) = Individual(g, f.toArray)
def vectorPhenotype = Individual.phenotype composeLens arrayToVectorLens
def buildIndividual[P](g: Genome, p: P) = Individual(g, p)
// def vectorPhenotype = Individual.phenotype composeLens arrayToVectorLens
def initialGenomes[M[_]: cats.Monad: Random](lambda: Int, continuous: Vector[C], discrete: Vector[D]) =
CDGenome.initialGenomes[M](lambda, continuous, discrete)
def adaptiveBreeding[M[_]: Generation: Random: cats.Monad: HitMap](
def adaptiveBreeding[M[_]: Generation: Random: cats.Monad: HitMap, P](
lambda: Int,
operatorExploration: Double,
discrete: Vector[D],
pattern: Vector[Double] Vector[Int]): Breeding[M, Individual, Genome] =
PSEOperations.adaptiveBreeding[M, Individual, Genome](
pattern: P Vector[Int]): Breeding[M, Individual[P], Genome] =
PSEOperations.adaptiveBreeding[M, Individual[P], Genome](
Individual.genome.get,
continuousValues.get,
continuousOperator.get,
discreteValues.get,
discreteOperator.get,
discrete,
vectorPhenotype.get _ andThen pattern,
Individual.phenotype[P].get _ andThen pattern,
buildGenome,
lambda,
operatorExploration)
def elitism[M[_]: cats.Monad: StartTime: Random: HitMap: Generation](pattern: Vector[Double] Vector[Int], continuous: Vector[C]) =
PSEOperations.elitism[M, Individual, Vector[Double]](
def elitism[M[_]: cats.Monad: StartTime: Random: HitMap: Generation, P: CanBeNaN](pattern: P Vector[Int], continuous: Vector[C]) =
PSEOperations.elitism[M, Individual[P], P](
i values(Individual.genome.get(i), continuous),
vectorPhenotype.get,
Individual.phenotype[P].get,
pattern)
def expression(phenotype: (Vector[Double], Vector[Int]) Vector[Double], continuous: Vector[C]): Genome Individual =
deterministic.expression[Genome, Individual](
def expression[P](phenotype: (Vector[Double], Vector[Int]) P, continuous: Vector[C]): Genome Individual[P] =
deterministic.expression[Genome, P, Individual[P]](
values(_, continuous),
buildIndividual,
phenotype)
......@@ -218,6 +218,18 @@ object NoisyPSEAlgorithm {
object PSE {
implicit def anyCanBeNan: CanBeNaN[Any] = new CanBeNaN[Any] {
override def isNaN(t: Any): Boolean = t match {
case x: Double x.isNaN