Consider the below C code. I would have thought that the variable bar
was being instantiated every time and would thus point to different addresses in memory, but it doesn't.
for (i = 2; i < 7; i++) {
struct foo bar;
printf("struct %u\n", bar);
}
Output:
struct 13205520
struct 13205520
struct 13205520
struct 13205520
struct 13205520
In case it is not obvious, what I want is to generate 5 different struct
s—well, actually 5 different pointers to struct
s—at 5 different locations. How can I do this?
A pointer variable is a variable (a name that references some area of memory), but what's in that area of memory? What's the pointer itself? Well, it's a memory address, a way of referencing another memory location.
You cant have variables stored in the same memory address. You can point to a memory address and store the value in that memory address to a different memory address. No YOU are wrong, that is not 2 variables at the same address, that is a variable and a reference to the same variable. A reference is not a variable.
Yes, two or more references, say from parameters and/or local variables and/or instance variables and/or static variables can all reference the same object.
The scope of bar
only exists within one iteration of the loop. That means that when the next struct foo
is created, it will be put in the same place as the old bar
, because as far as the compiler sees it, the bar
is no longer necessary. Looking at your example, it doesn't seem like you need to handle all of the bar
's at once. So you might be okay with them all being at the same location. However, if you need to deal with multiple at a time, I can think of two possible solutions.
To do this, you'll need an array of struct foo
's. The scope of the array needs to be outside of the loop. For example:
struct foo bar_list[5];
for (i = 2; i < 7; i++) {
printf("struct %p\n", (void *)&bar_list[i - 2]);
// use the foo's here
}
Then each iteration of your for loop can modify one of the values
If you're okay with storing five pointers in memory, you can allocate each bar somewhere on the heap. You would probably end up just using an array anyway, so this would probably only be useful if you needed to return the structs into another function. You'd need to do something like this:
struct foo* bar_list[5];
for (i = 2; i < 7; i++) {
bar_list[i - 2] = malloc(sizeof(struct foo));
printf("struct %p\n", (void *)bar_list[i - 2]);
// do anything else you need to do
}
It's also worth mentioning, as someone else pointed out, that %p
would be used to print a pointer address.
Your code has undefined behavior:
printf
to print its address, the conversion specifier %u
expects an unsigned int
, not a structure.bar
is uninitialized, passing it has undefined behavior.for
body for the next iteration.%p
and pass (void *)&bar
, but it is unspecified whether the address of bar
will be the same for each iteration or not.Most compilers will reuse the same space for bar
at each iteration, but a compiler could conceivably generate code to randomise the address of bar
in a proprietary way in order to make the code more resilient to exploits.
If you want all structures to reside in different addresses, you can define an array of structures outside the scope of the loop and print their addresses this way:
struct foo bar[5];
for (int i = 2; i < 7; i++) {
printf("address of struct bar[%d] is %p\n", i - 2, (void *)&bar[i - 2]);
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With