We are about to switch to a new forum software. Until then we have removed the registration on this forum.
Hello friends,
this is my very first post and I hope I'll do it fine. So here is my problem:
I am programming something like a evolutionary cellular automaton with multiple populations. Those populations move on the pixel grid and there are (by now) to options:
For the first case I see no problems. But for the second I would like the "world" to check the individuals fitness and decide who is allowed to "inhabit" the pixel-cell.
Again : Individual gets to cell which is == 0 => no problem Individual gets to cell which is != 0 => if it has better fitness the individual with lower fitness has to leave.
How can I get access to the cells fitnesses in the "world"?
Here is a reduced version of what I have right now.
(Sorry for my english by the way).
int[] indexState;
PImage img;
World w;
void setup()
{
size(400, 400);
img = createImage(width, height, RGB);
indexState = new int[width*height];
w = new World();
for (int i = 0;i<indexState.length;i++) {
indexState[i] = 0;
}
image(img, 0, 0);
loadPixels();
}
void draw()
{
w.run();
updateImage();
updatePixels();
}
void updateImage()
{
for (int i = 0;i<indexState.length;i++) {
if (indexState[i] == 0) {
pixels[i] = color(0);
}
else if (indexState[i] == 1) {
pixels[i] = color(255, 0, 0);
}
else if (indexState[i] == 2) {
pixels[i] = color(0, 255, 0);
}
}
}
class Cell
{
int index;
int fitness;
Cell(int _index)
{
index = _index;
fitness = int(random(100));
}
int getIndex()
{
return index;
}
int getFitness()
{
return fitness;
}
}
class Population
{
ArrayList<Cell> population = new ArrayList<Cell>();
int popIndex;
Population() {
int cellPosition = int(random(width*height));
population.add(new Cell(cellPosition));
}
void checkCellStats()
{
for (int i = 0;i<population.size();i++) {
Cell c = population.get(i);
int cIndex = c.getIndex();
indexState[cIndex] = popIndex;
}
}
void myIndexIs(int _popIndex) {
popIndex = _popIndex;
}
}
class World
{
ArrayList<Population> world = new ArrayList<Population>();
World()
{
world.add(new Population());
world.add(new Population());
}
void run()
{
for (int i = 0;i<world.size();i++) {
Population p = world.get(i);
int newIndex = i+1; // +1 because 0 is reserved for empty cells
p.myIndexIs(newIndex);
p.checkCellStats();
}
// Here is my problem
for (int i = 0;i<indexState.length;i++) {
if (indexState[i] != 0) { // if there is somebody
int whoIsThere = indexState[i]; // Which population is here?
Population atIndex = world.get(whoIsThere-1);
println("POPULATION " + whoIsThere + " IS AT INDEX " + i);
/* get Cell and its fitness?*/
}
}
}
}
Answers
You have indexState[] to check the state of each cell: empty, population 1, or population 2. However, you don't have an associated fitness array so looking up that information at the moment would be complicated / inefficient.
Maybe make another array for fitness that gets updated whenever indexState[] gets updated.
Edit: I did not address removing cells. Give me a minute and I'll put some code for a different way to think about the simulation.
Here is a simple grid version. Instead of there being a variable number of cells, everything is a cell but almost all of them are empty at the start. Two of them are initialized as being from different populations.
The advantage of this is that doing neighbor checks is simple. I did not go into details for cells on the edges and the growth rules should be changed to not bias the results. Right now, the double loop order affects assignment of new cells (left to right then top to bottom is the bias assignment order).
Hello there!
Thank you for answering! I think your code seems to be pretty uncomplicated compared to mine. I ' ll try it your way. Thank you very much!
Population has an array list of Cells. Either you expose the array list itself, or you add a getCell(int index) method to Population (and an access to the size of the list). This will allow to loop on the Population's Cells, and to get their values.
Thank you for answering!
Could you explain what you mean by "exposing the array list"?
I was trying to add a getCell method - but I coudn't figure out how to get access to the Cells position in the array list.
Would I maybe make sense to implement a personal "ID" in the cell constructor?
something like:
Cell(int index, int cellID) .. (by "ID" I mean the position in the array list.)
Than i could get two Cells from their Population classes in the World class and compare their fitnesses. Am I thinking right?
Sorry for my ignorance. This is kind of the first time I ll try to go my "own way of thinking" .. :)
By the way.. sorry for the duplicated post.
greetz!
Just add:
(properly formatted, lazy here...) to your Population class. (Actually, you can access it directly, but it is more "Java-ish", cleaner, this way...)
So you can get the list of cells in your atIndex population and iterate on it:
No need for an id for the cells, just access them this way, or by their index (get(i)).
Hello PhiLho - thank you for responding! That seems to be what I was searching for. But now it seems I made an error in reasoning, too.
Where and when would I decide if a Cell is allowed to stay at a location?
I would implement a "move" class in Population which would look something like that:
Is something like that possibile or do I have the World class make the decision? What would be the most efficient way, especially if i had thousands of cells.
Thank you very much for helping!
Greets