Page 1 of 1

Basic C question

PostPosted: Aug 9, 2002 @ 5:50am
by fzammetti
I know I'm going to feel stupid afterwards, but...

I have the following:

unsigned char* myArray[20];

What I want to be able to do is the following:

unsigned char* myPointer;
myPointer = myArray[0];
if (myPointer[3] == NULL) {
...

In other words, I want to have an array of unsigned char pointers and then have another single char pointer that points to the start of the array and still be able to access it as an array through the single pointer, indirectly so to speak.

(The problem I'm trying to solve is that I have a bunch of arrays of pointers to images that I iterate through, frames of animation actually, and when I call a certain function I need to check if the current frame's pointer is NULL, meaning I've reached the end of the animation sequence. The problem is, I can do this by a giant if block to check the correct array I'm currently using, but obviously it would be better if I could have a pointer to the array that I can access because that way the function doesn't have to know which sequence is currently in use. Make sense??)

I'm sure I have some basic syntax wrong somewhere. I figure, the first part of wisdom is being able to say "I don't know".

Well, consider me one wise bastard than! :)

PostPosted: Aug 9, 2002 @ 7:24am
by Jadam
dont you have to point towards the first adress of the array, and then incrementing the address basically increments the position in the array?

like wouldnt you have to use
MyPointer = &MyArray;

correct me if im wrong, i havent done C coding in a while...

PostPosted: Aug 9, 2002 @ 9:01am
by MirekCz
unsigned char* myPointer;
myPointer = myArray;
if (*(myPointer+3) == NULL) {
...
}

this one should work well - you assing the pointer to myarray table.. myarray[0] returns value of table, not pointer to it. it would work with &myarray[0]

the mypointer+3 points to myarray[3] and we use * to get the value of char placed in there. so
*(mypointer+3)

that's what I use in my anim lib.

PostPosted: Aug 9, 2002 @ 5:00pm
by fzammetti

PostPosted: Aug 9, 2002 @ 5:44pm
by Dan East

PostPosted: Aug 9, 2002 @ 11:08pm
by MirekCz
Dan, ehh, now I'm lost a bit.
if there's an array like char myarray[5];
we create a pointer char* mypointer;
and we set it to mypointer=myarray;
shouldn't it work just fine?
this way mypointer and myarray points to the beggining of table and you can easily use
*(mypointer+3) or mypointer[3] to get what you want.
or am I missing here something?

I don't see a reason for him to use a pointer that points to another pointer that points to the interesting bits.. (unless he's performing operations that could change table position in memory)

anyway here's how I take care of animations.
I use 5 bytes for every animation frame. I have got all data in one array of bytes, where first four bytes describe nr of anims and then there are 4 bytes pointers pointing to the beggining of following animations. I add one additional pointer at the end that points to last animation - to know when to stop playing it.

So my array looks like this:

4bytes - nr of anims
4bytes*nr of anims - pointers in array to start of animation
4bytes - last animation pointer
5xbytes*nr of frames in all anims - animation frames

reading data from it is easy:) looks like this
1.check if animation that we want to play is available (ie if we don't try to play animation 99 when there are only 90 prepared) - we use first 4 bytes for that
2.reading pointer to animation start
it's a bit tricky, what we need to do is:
a)calculate pointer to data about our animation start pointer (ie in the 4bytes*nr of anims array)

anima+4+(4*animmov)

where anima is our pointer to array, +4 to jump over nr of anims, +4*animmov to get to the anim we want to play

b)read pointer from there for ours animation
that's a bit more tricky.. looks like this:

(TUint8*) (anima+*((TUint32*)(anima+4+(4*animmov))));

so (TUint8*) tells compiler that we want a pointer
anima is the pointer to array
*((TUint32*)...) tells us how many bytes we need to move in order to get to first frame of animation that we desire to see

c)read pointer to next animation - so we know how many frames to play
this happens pretty much the same way as the earlier one(we just add 4 to read pointer to next animation).
By substracting those pointers and div by 5 we get nr of frames


Now when reading animation frames I do something like this:

anim->lastframeinfo[0..4] - to get specific bytes (lastframeinfo is TUint8* and points to actual animation frame)

to go to next frame I simply do anim->lastframeinfo+=5; and check if I don't try to play a frame that doesn't belong to this animation (if I do, I have to change animation to a different one)




Hope it makes at least a lil. sense to you:)

PS.Yes, I know noone will use it or learn anything from it.. I'm just happy about my code and can tell everyone around about it;) I know it by heart, actually;)

PostPosted: Aug 9, 2002 @ 11:40pm
by Dan East
Wow, that is probably a great deal more complicated than it needs to be. Of course C will let you take a chunk of RAM and go to the tedium of manually dividing it up and walking through the "elements" using raw math. However, if you simply use arrays and pointers properly you can allow the compiler to perform the pointer arithmetic for you, which leads to more readable code, as well as preventing the programmer from having to deal with the sizes of the elements (not to mention hardware-specific alignment issues).

Arrays are simply defined as:
type[size]

A pointer to the array is defined as:
type*

In his example, the array type is "char *", thus by the above definition a pointer to the array is "char **".

His array is not defined as char myarray[5], but char *myarray[5].

Dan East

PostPosted: Aug 10, 2002 @ 5:11pm
by MirekCz