92 lines
2.2 KiB
Plaintext
92 lines
2.2 KiB
Plaintext
bundle Default {
|
|
class Evolutionary {
|
|
target : static : String;
|
|
possibilities : static : Char[];
|
|
C : static : Int;
|
|
minMutateRate : static : Float;
|
|
perfectFitness : static : Int;
|
|
parent : static : String ;
|
|
rand : static : Float;
|
|
|
|
function : Init() ~ Nil {
|
|
target := "METHINKS IT IS LIKE A WEASEL";
|
|
possibilities := "ABCDEFGHIJKLMNOPQRSTUVWXYZ "->ToCharArray();
|
|
C := 100;
|
|
minMutateRate := 0.09;
|
|
perfectFitness := target->Size();
|
|
}
|
|
|
|
function : fitness(trial : String) ~ Int {
|
|
retVal := 0;
|
|
|
|
each(i : trial) {
|
|
if(trial->Get(i) = target->Get(i)) {
|
|
retVal += 1;
|
|
};
|
|
};
|
|
|
|
return retVal;
|
|
}
|
|
|
|
function : newMutateRate() ~ Float {
|
|
x : Float := perfectFitness - fitness(parent);
|
|
y : Float := perfectFitness->As(Float) * (1.01 - minMutateRate);
|
|
|
|
return x / y;
|
|
}
|
|
|
|
function : mutate(parent : String, rate : Float) ~ String {
|
|
retVal := "";
|
|
|
|
each(i : parent) {
|
|
rand := Float->Random();
|
|
if(rand <= rate) {
|
|
rand *= 1000.0;
|
|
intRand := rand->As(Int);
|
|
index : Int := intRand % possibilities->Size();
|
|
retVal->Append(possibilities[index]);
|
|
}
|
|
else {
|
|
retVal->Append(parent->Get(i));
|
|
};
|
|
};
|
|
|
|
return retVal;
|
|
}
|
|
|
|
function : Main(args : String[]) ~ Nil {
|
|
Init();
|
|
parent := mutate(target, 1.0);
|
|
|
|
iter := 0;
|
|
while(target->Equals(parent) <> true) {
|
|
rate := newMutateRate();
|
|
iter += 1;
|
|
|
|
if(iter % 100 = 0){
|
|
IO.Console->Instance()->Print(iter)->Print(": ")->PrintLine(parent);
|
|
};
|
|
|
|
bestSpawn : String;
|
|
bestFit := 0;
|
|
|
|
for(i := 0; i < C; i += 1;) {
|
|
spawn := mutate(parent, rate);
|
|
fitness := fitness(spawn);
|
|
|
|
if(fitness > bestFit) {
|
|
bestSpawn := spawn;
|
|
bestFit := fitness;
|
|
};
|
|
};
|
|
|
|
if(bestFit > fitness(parent)) {
|
|
parent := bestSpawn;
|
|
};
|
|
};
|
|
parent->PrintLine();
|
|
}
|
|
}
|
|
}
|
|
}
|