数组指针工作原理疑问:为何循环中cptr地址值持续变化?
为什么printf中的cptr输出递增的地址而非初始地址?
我课本上有这样一段代码:
char array[26]; char *cptr = array; char c; for(c = 'A'; c<('A'+26);c++) { *cptr ++=c ; printf("%d %c %d\n",cptr,c,c); }
我发现printf语句里的cptr输出的是递增的地址值(比如6487537、6487538这类),而不是一开始的初始地址6487536,想知道这是为什么?
嘿,这个问题的关键就藏在你写的*cptr ++=c ;这一行里!
这里的**后置递增运算符++**是核心:它的优先级比一元解引用*要高,所以这个表达式会被编译器解析成 *(cptr++) = c;,执行顺序是这样的:
- 首先,编译器会先记录当前
cptr指向的地址(用来后续做赋值操作) - 把变量
c的值赋值给这个地址对应的内存位置(也就是array数组里的当前元素) - 最后,立刻把
cptr本身的地址值加1,让它指向数组的下一个char位置
所以等你执行完这行赋值代码,再调用printf的时候,cptr已经不是最初指向array开头的那个地址了——它已经自增过一次。循环每跑一轮,cptr就会往后挪一个字节(因为char类型占1字节),所以每次printf输出的地址自然是一步步递增的。
如果你想在printf里输出每次赋值的那个地址(或者初始地址),可以改写成这两种方式:
// 方式1:拆分赋值和自增操作,先输出再挪指针 *cptr = c; printf("%d %c %d\n", cptr, c, c); // 这里输出的就是当前赋值的地址 cptr++; // 方式2:利用自增后的指针回退,输出刚赋值的地址 *(cptr++) = c; printf("%d %c %d\n", cptr - 1, c, c); // cptr已经自增,减1就是刚才赋值的地址
这样就能得到你预期的地址输出啦。
内容的提问来源于stack exchange,提问作者Barton Yon
相关产品推荐
相关产品推荐

