C语言表达式++*ptr++求值顺序疑问:为何后置自增未先执行?
表达式
++*ptr++的求值解析 很多人会混淆运算符优先级和求值顺序,这就是你困惑的根源。先明确两个关键概念:
- 优先级:决定运算符与操作数的绑定关系,不是执行顺序;
- 求值顺序:表达式中各操作数的计算顺序,C语言中多数情况下未指定,但部分运算符有明确的求值规则。
按优先级拆解表达式
C语言中运算符优先级从高到低:后置自增++ > 解引用* > 前置自增++。所以++*ptr++的绑定关系等价于:
++(*(ptr++))
拆解逻辑:
- 后置自增
ptr++先与ptr绑定,它会返回ptr当前的地址值,同时产生副作用(ptr的地址往后偏移1位); - 解引用
*作用于ptr++返回的原地址,拿到该地址存储的字符值; - 前置自增
++作用于解引用得到的字符值,将其加1。
结合代码实例分析
你的代码逻辑是遍历字符串,把每个字符加1,直到遇到结束符'\0':
int main() { char arr[] = "iitbforgoodlife"; char *ptr = arr; while(*ptr != '\0') ++*ptr++; printf("%s %s", arr, ptr); getchar(); return 0; }
循环中每次执行++*ptr++的具体过程:
- 第一次循环:
ptr指向arr[0](值为'i'),ptr++返回arr[0]的地址,同时ptr移动到arr[1];解引用拿到'i',前置++把它改成'j',此时arr[0] = 'j'; - 第二次循环:
ptr指向arr[1](值为'i'),重复上述操作,arr[1]变成'j',ptr移动到arr[2]; - 以此类推,直到
ptr指向'\0'时循环终止。此时arr中每个字符都被加1,得到结果jjucgpshppemjgf;而ptr指向'\0'的下一个位置,第二个%s会输出空(或随机乱码,取决于内存内容,实际运行中因'\0'后无有效字符,通常显示为空)。
常见误区澄清
你觉得后置自增没“优先触发”,是把优先级和执行顺序搞混了:
- 后置自增的优先级高,仅代表它和
ptr先绑定,不意味着它的副作用(ptr加1)要先于其他操作执行; ptr++的返回值是ptr原来的地址,解引用和前置++都是基于这个原地址的字符操作,ptr的地址增加是副作用,会在整个表达式执行完成前的某个时间点完成,但不影响当前对原地址字符的修改。
内容的提问来源于stack exchange,提问作者Yuu
相关产品推荐
相关产品推荐

