As a follow up to this question: How do you specify variables to be final in C?, I've been playing around with const variables. In particular, I've written and compiled the following program:
#include<stdio.h>
int main(void) {
const int i = 5;
int* i_ptr = &i;
*i_ptr = *i_ptr + 1; // (1)
printf("%d %d\n", *i_ptr, i);
int j = 10;
const int* j_ptr = &j;
j_ptr = i_ptr; // (2)
printf("%d %d\n", *j_ptr, j);
return 0;
}
I'm working with the following gcc compiler:
$ gcc --version
Apple LLVM version 8.1.0 (clang-802.0.42)
Target: x86_64-apple-darwin16.5.0
Thread model: posix
In the code listing, I've marked two lines of code that behave differently than I'd expect:
- (1) I would expect the compiler to spit at me for trying to modify the
constvariableithati_ptrbut to my surprise it does not. - (2) I would expect another error to be generated here because
j_ptrhas just been declaredconstand now modifying it is perfectly okay.
Further more, here is the output I get:
6 5
6 10
What's surprising here is that, in the first line out output, i_ptr and i do not have the same values here. What gives? I certainly didn't call malloc and assign i_ptr to new memory.
So how is it pointing to something besides i?
What's even more puzzling is that, if I replace line (2) with this:
*j_ptr = *j_ptr + 1;
I get
error: read-only variable is not assignable
I'd expect that, since j_ptr is pointing to non-const variable j, it should increment j. But that doesn't happen.
I'd really appreciate if someone could explain my observations, as I can't seem to come up with any reasons for why these const pointers should behave this counter-intuitively.