C pointer and arrays, help please

Other misc things
Post Reply
User avatar
GerardWassink
New member
Posts: 8
Joined: Sun Dec 11, 2022 10:49 am

C pointer and arrays, help please

Post by GerardWassink »

Hi guys,
Recently downloaded Z88DK to be able to generate executables for my RC2014 Z80 CPM machine.
It's been a while since I programmed in C.
I am working on a version of 'game of life' as designed by John Conway.
For that I defined two array's of 16 rows and 64 columns.
I declare these as follows:

Code: Select all

#define MAXROW 15
#define MAXCOL 63

....

static char *grid1[MAXROW+1] = {
        " *                                                              ",
        "**    *                                                         ",
        "       *                                                        ",
        "     ***                                                        ",
.... another 10 lines of spaces ....
        "                                                                ",
        "                                                                "
};
now I declared pointers to those grids:

Code: Select all

char **lifeGrid = NULL;
char **nextGrid = NULL;
and initialize them as follows:

Code: Select all

    lifeGrid = grid1;
    nextGrid = grid2;
Now I iterate thru them:

Code: Select all

    while (!done) {
        displayLifeGrid();		// using pointer 'lifeGrid'
        nextGeneration();		// clear the next generation Grid and calculate it anew from the lifeGrid
        swapGrids();			// swap the lifeGrid and nextGrid pointer
    }
In nextGeneration, the iteration goes as follows:

Code: Select all

    for (currentRow = 0; currentRow <= MAXROW; currentRow++) {
        for (currentCol = 0; currentCol <= MAXCOL; currentCol++) {
            // referring to cells like:
            if (lifeGrid[currentRow][currentCol] != ' ') // do stuf
        }
    }
I extensively tested the displaying of the grids, the swapping of the pointers (a couple of times in a row) and found that that's all working.
However while running it gives some unexpected results.

Question: Am I handling the definition of these grids properly?

Any help appreciated!

Gerard
User avatar
GerardWassink
New member
Posts: 8
Joined: Sun Dec 11, 2022 10:49 am

Re: C pointer and arrays, help please

Post by GerardWassink »

In the meantime, I got it to work by fiddling around a bit and simplifying the constructs.

The changed definitions of the grids and their pointers:

Code: Select all

static char grid1[(MAXROW+1)*(MAXCOL+1)];       // grids are one continuous
static char grid2[(MAXROW+1)*(MAXCOL+1)];       //  'line' of characters

char *lifeGrid;
char *nextGrid;
In the routine 'nextGeneration, the iteration and references now go as follows:

Code: Select all

    for (currentRow = 0; currentRow <= MAXROW; currentRow++) {
        for (currentCol = 0; currentCol <= MAXCOL; currentCol++) {
            ....
            if (lifeGrid[currentRow*(MAXCOL+1)+currentCol] == ' ') {  // *** Do stuff
            ....
        }
    }
game of life is working now, albeit rather slow...
User avatar
jorgegv
Well known member
Posts: 287
Joined: Wed Nov 18, 2020 5:08 pm

Re: C pointer and arrays, help please

Post by jorgegv »

GerardWassink wrote: Sun Dec 11, 2022 11:08 am
I extensively tested the displaying of the grids, the swapping of the pointers (a couple of times in a row) and found that that's all working.
However while running it gives some unexpected results.

Question: Am I handling the definition of these grids properly?

Any help appreciated!

Gerard
In my opinion it's a bit difficult to help you if you do not describe what those "unexpected results" are or show us the complete code so that we can see what the code is trying to do.

I see you are using 2-dimensional arrays created by using the standard two ways in C: a) a pointer to a table of pointers, which allows you to directly use the familiar "a[row][col]" syntax; and b) an MxN linear table which is addressed by "a[row*NUM_COLS + col]". So far it seems you are declaring and accessing them correctly, but the only sensible thing I can check are the typical off-by-one errors...

Regarding performance, it's no wonder why the working code may be slower than the first: you have 2 nested loops (=cuadratic work) and the work inside the inner loop includes a multiplication in your second version of the code, while in the first one it's doing only pointer arithmetic (additions). The slightest difference in computation time is going to be greatly magnified by the quadratic factor of your loops.
User avatar
feilipu
Member
Posts: 45
Joined: Tue Nov 15, 2016 5:02 am

Re: C pointer and arrays, help please

Post by feilipu »

Conway Life is hard to optimise, because it reaches across arrays to get neighbouring cells, that aren’t adjacent in memory. All you can do is minimise those accesses.

Like everyone else, I’ve got a version (that I know works with z88dk). It is in my libraries for z88dk, here.

Cheers, Phillip
User avatar
GerardWassink
New member
Posts: 8
Joined: Sun Dec 11, 2022 10:49 am

Re: C pointer and arrays, help please

Post by GerardWassink »

Thanks for the help guys, here's a version of my entire code.

Mind you, it is fully scalable. Just change the MAXROW and MAXCOL definitions. I had it run on a raspberry pi (albeit with a couple of minor alterations, and it is blazing fast there with 128 columns and 64 rows!

Gerard
User avatar
feilipu
Member
Posts: 45
Joined: Tue Nov 15, 2016 5:02 am

Re: C pointer and arrays, help please

Post by feilipu »

Looks very clean. Will try it out soon.

Perhaps just to suggest that the z88dk memset() function implementation is very optimised (for each machine type), so perhaps using that string function to clear the screen may save a few cycles and speed things up for you.
User avatar
jorgegv
Well known member
Posts: 287
Joined: Wed Nov 18, 2020 5:08 pm

Re: C pointer and arrays, help please

Post by jorgegv »

GerardWassink wrote: Thu Dec 15, 2022 10:53 am Thanks for the help guys, here's a version of my entire code.
What about the version of your code that does not work? Accordin to youre previous messages, this is the one that works?

And what were the "unexpected results" you had?
User avatar
GerardWassink
New member
Posts: 8
Joined: Sun Dec 11, 2022 10:49 am

Re: C pointer and arrays, help please

Post by GerardWassink »

jorgegv wrote: Thu Dec 15, 2022 11:12 am
What about the version of your code that does not work? Accordin to youre previous messages, this is the one that works?

And what were the "unexpected results" you had?
I'm sorry to say that I did not keep that version. The version I posted above is the working one...

Gerard
User avatar
jorgegv
Well known member
Posts: 287
Joined: Wed Nov 18, 2020 5:08 pm

Re: C pointer and arrays, help please

Post by jorgegv »

well, so everything works then, no problem to solve.
User avatar
GerardWassink
New member
Posts: 8
Joined: Sun Dec 11, 2022 10:49 am

Re: C pointer and arrays, help please

Post by GerardWassink »

jorgegv wrote: Thu Dec 15, 2022 12:44 pm well, so everything works then, no problem to solve.
Indeed, thanks anyway!

Gerard
User avatar
GerardWassink
New member
Posts: 8
Joined: Sun Dec 11, 2022 10:49 am

Re: C pointer and arrays, help please

Post by GerardWassink »

feilipu wrote: Thu Dec 15, 2022 11:10 am Looks very clean. Will try it out soon.

Perhaps just to suggest that the z88dk memset() function implementation is very optimised (for each machine type), so perhaps using that string function to clear the screen may save a few cycles and speed things up for you.
Would you mind to elaborate on that function please? How doe it work and how would it replace the printf() I used in there?
User avatar
jorgegv
Well known member
Posts: 287
Joined: Wed Nov 18, 2020 5:08 pm

Re: C pointer and arrays, help please

Post by jorgegv »

GerardWassink wrote: Thu Dec 15, 2022 1:05 pm ind to elaborate on that function please? How doe it work and how would it replace the printf() I used in there?
I suppose he means that you could replace your clearNextGen() function with:

Code: Select all

void clearNextGen() {
    memset( nextGrid, ' ', (MAXCOL+1)*(MAXROW+1));
}
User avatar
GerardWassink
New member
Posts: 8
Joined: Sun Dec 11, 2022 10:49 am

Re: C pointer and arrays, help please

Post by GerardWassink »

jorgegv wrote: Thu Dec 15, 2022 1:34 pm I suppose he means that you could replace your clearNextGen() function with:

Code: Select all

void clearNextGen() {
    memset( nextGrid, ' ', (MAXCOL+1)*(MAXROW+1));
}
Okay, thanks, I did that and it works flawlessly. I have the impression that it is slightly faster now.
See my repo on GitHub...
Post Reply