davidrmiller / biosim4

Biological evolution simulator
Other
3.18k stars 452 forks source link

Pair check is incorrect #79

Closed altivecer closed 2 years ago

altivecer commented 2 years ago

In survival-criteria.cpp, in the case CHALLENGE_PAIRS there is a pair of for loops that have a bad check for the end of the loop

        for (int16_t x = indiv.loc.x - 1; x < indiv.loc.x + 1; ++x) {
            for (int16_t y = indiv.loc.y - 1; y < indiv.loc.y + 1; ++y) {

should be

        for (int16_t x = indiv.loc.x - 1; x <= indiv.loc.x + 1; ++x) {
            for (int16_t y = indiv.loc.y - 1; y <= indiv.loc.y + 1; ++y) {

same issue for the inner pair.

                        for (int16_t x1 = tloc.x - 1; x1 < tloc.x + 1; ++x1) {
                            for (int16_t y1 = tloc.y - 1; y1 < tloc.y + 1; ++y1) {

should be

                        for (int16_t x1 = tloc.x - 1; x1 <= tloc.x + 1; ++x1) {
                            for (int16_t y1 = tloc.y - 1; y1 <= tloc.y + 1; ++y1) {
davidrmiller commented 2 years ago

Great catch! I'm testing it now and the results of that challenge are much better behaved. Thanks for finding and reporting this.

altivecer commented 1 year ago

Hi David,

When I was trying to figure out what was wrong with the death check I added the following to simulator.cpp just before endOfGenerations(generation); It really helped and made watch a generation much more satisfying.

define SAVE_POST_DEATH_FRAME 1

ifdef SAVE_POST_DEATH_FRAME

            // kill any cell that is going to die execpt for the ALTRUISM cases becasue I'm note sure what to do there
            int numAlive = p.population;
            if (p.challenge != CHALLENGE_ALTRUISM && p.challenge != CHALLENGE_ALTRUISM_SACRIFICE)
            {
                for (uint16_t index = 1; index <= p.population; ++index)
                {
                    std::pair<bool, float> passed = passedSurvivalCriterion(peeps[index], p.challenge);
                    if (!passed.first)
                    {
                        peeps[index].willDie=true;
                        --numAlive;
                    }
                }
                for (uint16_t index = 1; index <= p.population; ++index)
                {
                    if (peeps[index].willDie)
                    {
                        peeps[index].alive=false;
                        grid.set(peeps[index].loc, 0);
                    }
                }
            }
            // Save one final frame of video
            endOfSimStep(p.stepsPerGeneration, generation);

endif

Also updated Indic.h to add willDie

struct Indiv { bool alive; bool willDie;

And indiv.cpp to initialize willDie to false.

void Indiv::initialize(uint16t index, Coord loc, Genome &&genome) { index = index; loc = loc; //birthLoc = loc; grid.set(loc, index_); age = 0; oscPeriod = 34; // ToDo !!! define a constant alive = true; willDie = false;

davidrmiller commented 1 year ago

Thanks, looks interesting.