【发布时间】:2014-01-16 10:47:42
【问题描述】:
我想使用指针编写合并排序,但是当我尝试在 C 中执行此操作时,我遇到了分段错误。我预计会出现分段错误,但不是我实际得到它的地方。这是我的代码:
#include <stdio.h>
#include <stdlib.h>
int *merge(int [], int *, int *, int *);
int *mergesort(int [], int *, int *);
int main(){
int n[] = {4, 2, 9, 5, 10, 11, 1, 0};
int *m = mergesort(n, n, n + 7);
int i;
for(i = 0; i < 7; i++)
printf("[%d]\n", n[i]);
return 0;
}
int *mergesort(int *a, int *p, int *r){
if(p >= r)
return a;
int *q = p + (q - p)/2;
mergesort(a, p, q);
mergesort(a, q+1, r);
return merge(a, p, q, r);
}
/*0, 1, 2, 3, 4, 5, 6, 7*/
int *merge(int *a, int *p, int *q, int *r){
/*int *arrone = new int[q - p + 1];
int *arrtwo = new int[r - q]; */
int *arrone = malloc(sizeof(int) * (q - p + 1));
int *arrtwo = malloc(sizeof(int) * (r - q));
int i;
for(i = 0; p + i <= q; i++)
arrone[i] = p[i];
for(i = 0; q + i + 1 <= r; i++)
arrtwo[i] = *(q + 1 + i);
int j;
for(j = 0; arrone <= q && arrtwo <= r; j++){
if(*arrone < *arrtwo)
a[j] = *arrone, arrone++;
else
a[j] = *arrtwo, arrtwo++;
}
if(arrone <= q)
for(; p + j <= r; j++)
a[j] = *arrone++;
else
for(; p + j <= r; j++)
a[j] = *arrtwo++;
free(arrone);
free(arrtwo);
return a;
}
现在奇怪的是,我在第一次调用 mergesort 时就遇到了这个分段错误。在 DDD 中,它一接触这个函数就会出错。 DDD 给了我这个
程序收到信号SIGSEGV,分段错误。 (很长 地址)在合并排序中(a
然而,当我回溯它时,它会在合并中调用第二个合并排序的行提供无限数量的调用,尽管我不明白为什么这与调用第一个合并排序的地方有任何不同(实际上那一个也在我的 gdb 回溯的第 0 帧中突出显示)
这次我做错了什么?
【问题讨论】:
-
arrone <= q && arrtwo <= r无意义 -
我不知道怎么做。循环继续,直到 arrone 或 arrtwo 点超出其上限。我就是这样检查的。
-
arrone和arrtwo是由malloc返回分配的内存地址。它独立于q和r。 -
你是对的,让我来解决这个问题。
-
free(arrone);注意,如果你改了arrone,就不能free(arrone)了。
标签: c sorting pointers segmentation-fault dynamic-memory-allocation