views:

134

answers:

6

How can we access variables of a structure? I have a struct:

typedef struct {
   unsigned short a;
   unsigned shout b;
} Display;

and in my other class I have a method:

int NewMethod(Display **display)
{
   Display *disp=new Display();
   *display = disp;
   disp->a=11;
}

What does **display mean? To access variables of struct I have used ->, are there other methods too?

A: 

**display is just a double pointer (a pointer to a pointer of type Display).

Taylor Leese
A: 

The ** means that its a pointer-to-a-pointer. Basically it points to another pointer that then points to something else, in your case a Display structure.

If you called the function with only the object you can access the members with the . operator.

int NewMethod(Display display)
{
Display disp = display;
disp.a=11;
}

But this way you are not modifying directly the Display display object but a local copy. Your code suggests that the changes to the object are needed outside of the function so your only option is the one you described (well, maybe passing the argument by refference but the syntax then would more or less the same (->)).

Ezekiel Rage
+5  A: 

As Taylor said, the double asterisk is "pointer to pointer", you can have as many levels of pointers as you need.

As I'm sure you know, the arrow operator (a->b) is a shortcut for the asterisk that dereferences a pointer, and the dot that accesses a field, i.e.

a->b = (*a).b;

The parentheses are necessary since the dot binds tighter. There is no such operator for double asterisks, you have to first de-reference to get to the required level, before accessing the fields:

Display **dpl = ...;

(*dpl)->a = 42;

or

(**dpl).a = 42;
unwind
Damn! I didnt think of that. Good answer.
Ezekiel Rage
A: 

Since disp is a Pointer you have to use ->

If you just have a "normal" variable (i.e. on the stack) Display d;

you can write d.a

A struct is the same as a class. The only difference (I am aware of) is that all members are public by default.

jens
A: 

You can do (*disp).a=11;

it is called dereferencing

PoweRoy
+2  A: 

Think of it as *(*display). When you want to pass the address of an integer to a function so that you can set the integer, you use:

void setTo7 (int *x) {
    *x = 7;
}
: : :
int a = 4;
setTo7 (&a);
// a is now 7.

It's no different from what you have except that you want to set the value of a pointer so you need to pass the pointer to that pointer. Simple, no?

Try this out:

#include <stdio.h>
#include <string.h>

static void setTo7 (int *x) { *x = 7; }

void appendToStr (char **str, char *app) {
    // Allocate enough space for bigger string and NUL.

    char *newstr = malloc (strlen(*str) + strlen (app) + 1);

    // Only copy/append if malloc worked.

    if (newstr != 0) {
        strcpy (newstr, *str);
        strcat (newstr, app);
    }

    // Free old string.

    free (*str);

    // Set string to new string with the magic of double pointers.

    *str = newstr;
}

int main (void) {
    int i = 2;
    char *s = malloc(6); strcpy (s, "Hello");
    setTo7 (&i); appendToStr (&s, ", world");
    printf ("%d [%s]\n",i,s);
    return 0;
}

The output is:

7 [Hello, world]

This will safely append one string value to another, allocating enough space. Double pointers are often used in intelligent memory allocation functions, less so in C++ since you have a native string type, but it's still useful for other pointers.

paxdiablo