Question

I am building a version of the Game of Life in ANSI C and I have almost all of the code written for it.

My C source file:

#include <stdio.h>
#include <stdlib.h>

#define HEIGHT 32
#define WIDTH 32
#define COMPASS 8
#define SPACE '.'

unsigned long mask = 0x80000000;
unsigned long neighbours[COMPASS] = { 0 };
unsigned long row[WIDTH] = { 0 };
unsigned long copy[WIDTH] = { 0 };

int northWest(unsigned long row, int rowNum) {
    copy[rowNum - 1] = row >>= 1;
    return copy[rowNum - 1];
}

int north(unsigned long row, int rowNum) {
    copy[rowNum - 1] = row;
    return copy[rowNum - 1];
}

int northEast(unsigned long row, int rowNum) {
    copy[rowNum - 1] = row <<= 1;
    return copy[rowNum - 1];
}

int west(unsigned long row, int rowNum) {
    copy[rowNum] = row >>= 1;
    return copy[rowNum];
}

int east(unsigned long row, int rowNum) {
    copy[rowNum] = row <<= 1;
    return copy[rowNum];
}

int southWest(unsigned long row, int rowNum) {
    copy[rowNum + 1] = row >>= 1;
    return copy[rowNum + 1];
}

int south(unsigned long row, int rowNum) {
    copy[rowNum + 1] = row;
    return copy[rowNum + 1];
}

int southEast(unsigned long row, int rowNum) {
    copy[rowNum + 1] = row <<= 1;
    return copy[rowNum + 1];
}

/*void clearRows(unsigned long row[]) {
    int i;
    system("clear");
    for (i = 0; i < HEIGHT; ++i) {
        row[i] = 0;
    }
}*/

void displayBinary(unsigned long x) {
    int bit;
    int mask;
    for (bit = 0; bit < HEIGHT; ++bit) {
        mask = 1 << bit;
        printf("%c", (x & mask) ? 'X' : SPACE);
    }
    printf("\n");
}

int main(void) {
    int i, alive;
    char ch;
    unsigned long init32;
    srand(time(NULL));

    for (i = 0; i < HEIGHT; ++i) {
        init32 = ((double)rand() / RAND_MAX) * 0xFFFFFFFF;
        row[i] = init32;
        displayBinary(row[i]);
    }

    do {
        system("clear");
        for (i = 0; i < HEIGHT; ++i) {
            neighbours[0] = north(row[i], i);
            neighbours[1] = south(row[i], i);
            neighbours[2] = west(row[i], i);
            neighbours[3] = east(row[i], i);
            neighbours[4] = northWest(row[i], i);
            neighbours[5] = northEast(row[i], i);
            neighbours[6] = southEast(row[i], i);
            neighbours[7] = southWest(row[i], i);
        }
        for (i = 0; i < HEIGHT; ++i) {
            alive += ((mask & neighbours[i]) ? 1 : 0);
            displayBinary(row[i]);
        }
    } while ((ch = getchar()) != 'n');

    return EXIT_SUCCESS;
}

What I am aiming for here is to have random 'X' characters printed on a 32x32 board, and have the program loop as long as the user does not type 'n'. For each loop iteration, I would like each coordinate to check its neighbours and "die" if it has less than two neighbours or more than three neighbours. Otherwise, it "lives" and an 'X' is printed at that coordinate.

I understand using bitwise ANDing may not be the best way to complete this, but my professor has asked we use bitwise AND, and so therefore I cannot change that logic.

I am having trouble clearing the rows between loops. Could somebody please help me figure out how to print the updated rows for each iteration of the do loop?

Any help is much appreciated. Thank you.

Was it helpful?

Solution

In order to show what is going on, I added this define,

//#define SPACE (0x20)
#define SPACE ('.')

Then I changed both instances where you printed space,

printf("%c", 0x20);

to

printf("%c", SPACE);

And then ran your program and got a single line, with some "." and some "X", but the second pass resulted in all ".",

Looks like your calculation of adjacent nodes might be wrong.

Why does your print appear wrong?

Because your first COMPASS loop uses displayBinary() 8 times,

for (i = 0; i < COMPASS; ++i) {
    init32 = ((double)rand() / RAND_MAX) * 0xFFFFFFFF;
    row[i] = init32;
    displayBinary(row[i]);
}

While your subsequent looks use printf (rather than calling displayBinary), 8 times to only print 8 characters,

    for (i = 0; i < COMPASS; ++i) {
        alive += ((mask & row[i]) ? 1 : 0);
        if ((alive == 2) || (alive == 3))
            printf("%c", 'X');
        else
            printf("%c", SPACE);
    }

Your HEIGHT loop does a recalculation of neighbours[], but you should be reseting row[].

I rewrote your displayBinary function, and this displays the entire row,

void displayBinary(unsigned long x) {
    //do {
    //    printf("%c", (x & mask) ? 'X' : SPACE);
    //} while ((mask >>= 1) != 0);
    int bit;
    int mask;
    for( bit=0; bit<32; ++bit )
    {
        mask = 1<<bit;
        printf("%c", (x & mask) ? 'X' : SPACE);
    }
    printf("\n");
}
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top