我正在编写一些东西来模拟进化,但是使用经过测试的方程式来找到算法的digitum。基本上它的作用是创建GENERATION
Organisms
,其中DNABITS
int
s,并执行
((dna[0] & i) / i) + ((dna[1] & i) / i)...
然后将其与真实的数字进行比较,并将两个有机体的差异最小化。但是出于某种原因,一代人的平均差异从大约486,000 / 487,000开始,然后有时会下降,但随后总会回到大约那个范围。是什么导致了这种行为?
public class CodeEvolution {
public static final int DNABITS = 30;
public static final int MUTATION = 5;
public static final int PARENT = 1000;
public static final int GENERATION = 10;
public static final int TEST = 1000;
public static final int RETURNTHRESHOLD = 10;
public static Random rand = new Random();
static boolean firsttime = true;
static Organism[] generation;
static int[] difference;
public static void main(String[] args) throws NumberFormatException, IOException {
long time = System.currentTimeMillis();
Organism finalorg = iterate();
System.out.println("TIME: " +(System.currentTimeMillis() - time));
for(int i = 0; i < finalorg.DNA.length; ++i){
System.out.println(finalorg.DNA[i]);
}
BufferedReader r = new BufferedReader(new InputStreamReader(System.in));
while(true)
System.out.println(finalorg.digitSum(Integer.parseInt(r.readLine())));
}
public static Organism iterate(){
while(true){
if (firsttime){
firsttime = false;
generation = new Organism[GENERATION];
for (int i = 0; i < GENERATION; i++){
generation[i] = Organism.parent(); //spawn first organisms
}
}
difference = getDifferences(generation);
int closest1 = Integer.MAX_VALUE;
int closest2 = Integer.MAX_VALUE;
Organism orgclosest1 = Organism.parent();
Organism orgclosest2 = Organism.parent();
System.out.println(average(difference));
for (int i = 0; i < GENERATION; i++){
if(Math.abs(difference[i]) <= RETURNTHRESHOLD && Math.abs(difference[i]) >= -RETURNTHRESHOLD){
return generation[i];
}
if(Math.abs(difference[i]) < closest1){
orgclosest2 = orgclosest1;
orgclosest1 = generation[i];
closest2 = closest1;
closest1 = Math.abs(difference[i]);
}
else if (Math.abs(difference[i]) < closest2 && Math.abs(difference[i]) != closest1){
closest2 = Math.abs(difference[i]);
orgclosest2 = generation[i];
}
}
//orgclosest1 = parent 1, etc
for(int i = 0; i < GENERATION; ++i)
generation[i] = Organism.child(orgclosest1, orgclosest2);
}
}
private static double average(int[] data) {
int sum = 0;
for (int d : data) sum += d;
return 1.0d * sum / data.length;
}
public static int[] getDifferences(Organism[] parents){
int[] differencescore = new int[parents.length];
for(int i = 0; i < parents.length; ++i){
for(int x = 1; x < TEST; ++x){
int sum = realSumDigits(x);
int orgSum = parents[i].digitSum(x);
differencescore[i] += orgSum - sum;
}
}
return differencescore;
}
private static int realSumDigits(int digits) {
int sum = 0;
while ( digits > 0 )
{
sum += digits % 10;
digits /= 10;
}
return sum;
}
}
Organism.java
public class Organism {
int[] DNA; //((i & d) / d) +...
public Organism(int[] DNA){
this.DNA = DNA;
}
public int digitSum(int x){
for (int i = 0; i < DNA.length; ++i){
if (DNA[i] != 0)
x += (x & DNA[i]) / DNA[i];
}
return x;
}
public static Organism child(Organism p1, Organism p2){
int[] DNA = new int[CodeEvolution.DNABITS];
for (int i = 0; i < DNA.length; i++){
DNA[i] = average(p1.DNA[i], p2.DNA[i]) + random(CodeEvolution.MUTATION);
}
return new Organism(DNA);
}
public static Organism parent(){
int[] DNA = new int[CodeEvolution.DNABITS];
for (int i = 0; i < DNA.length; i++){
DNA[i] = random(CodeEvolution.PARENT) + (CodeEvolution.PARENT/2);
}
return new Organism(DNA);
}
private static int random(int mutation) {
return CodeEvolution.rand.nextInt(mutation) - (mutation/2);
}
private static int average(int i, int j) {
return (i + j)/2;
}
}
修改 也许我应该改变基于DNA的方程式来找到每个生物的数字?你会建议什么?
答案 0 :(得分:0)
没有&#34;正确&#34;这样做的方式。我的建议是创建一个锦标赛选择功能(你目前没有我看到的)来匹配两(2)个足够好的父母来创造下一个生物。这就是你的进化如何运作:)