快速排序实现中两种swap调用方式的差异咨询
快速排序中两种swap调用的差异解析
在实现快速排序时,发现两种swap调用行为截然不同:swap(&base_array[left], &base_array[right])会导致数组排序异常,而swap(base_array + left, base_array + right)能正常工作,相关代码如下:
void swap(int *a, int *b) { int temp = *a; *a = *b; *b = temp; } int *base_array; int left; int right; // 导致排序异常的调用 swap(&base_array[left], &base_array[right]); // 正常工作的调用 // swap(base_array + left, base_array + right);
核心结论:两种写法语法语义完全等价
从C语言规则来看,&base_array[left]和base_array + left是完全等价的:
base_array[left]的本质是*(base_array + left),即对指针base_array偏移left个int长度后的地址解引用;- 对
base_array[left]取地址&*(base_array + left),编译器会直接优化为base_array + left——解引用和取地址操作相互抵消,最终得到的是同一个内存地址。
出现差异的原因:代码存在未定义行为
既然写法等价,那出现行为差异的根源必然是代码中存在未定义行为,不同写法在编译或执行时触发了不同的错误表现:
- 索引越界:如果
left或right的值超出了base_array指向数组的合法范围,两种写法都会访问非法内存,但编译器优化策略不同可能导致错误表现不一致; - base_array指针被意外修改:如果在swap调用前,
base_array被错误地指向了其他内存区域,而left/right是基于原数组的偏移量,此时base_array[left]会访问错误的内存位置; - 变量未初始化:如果
left或right没有被正确赋值,其值为随机垃圾值,两种写法都会访问随机内存,但表达式的计算顺序差异可能导致不同的错误结果。
排查建议
重点检查以下几点:
- 确认
left和right始终是数组的合法索引,没有越界; - 检查
base_array指针在整个排序过程中是否被意外修改(比如被重新赋值); - 确保
left、right变量在使用前已被正确初始化。
内容的提问来源于stack exchange,提问作者Solruhama
相关产品推荐
相关产品推荐

