【发布时间】:2017-09-10 14:25:01
【问题描述】:
我想知道为什么我为桶排序实现的这个算法会导致分段错误。似乎实现中的所有内容都运行良好,但可能有一些变量 n 应该是 n+1 或其他;我在弄清楚这一点时遇到了一些困难。
我是按照this video中描述的来实现的。
#include <stdio.h>
#include <stdlib.h>
void insertion(int * array, int n){
// insertion sort
int i = 1, j = 0, temp;
while(i < n){
j = i;
while(j > 0 && array[j-1] > array[j]){
temp = array[j-1];
array[j-1] = array[j];
array[j] = temp;
--j;
}
++i;
}
}
void bucket(int * array, int n){
int max,i,j,k,size, div, pos;
int ** buckets, *bucket_position;
//Find maximum value in array
max = array[0];
for(i=0;i<n;++i) if( max < array[i] ) max = array[i];
//Determine amount of buckets and creates them
size = max / n;
buckets = (int**) malloc(sizeof(int*) * size);
for(i=0;i<size;++i){
buckets[i] = (int*) malloc(sizeof(int) * max);
}
bucket_position = (int*) malloc(sizeof(int) * size);
for(i=0;i<size;++i) bucket_position[i] = 0;
//Copy array values into the buckets
div = (max+1) / size;
if( (max+1) % size ) ++div;
for(i=0;i<n;++i){
pos = array[i] / div;
buckets[pos][bucket_position[pos]] = array[i];
++bucket_position[pos];
}
//Take values out of the buckets into the array
k = 0;
for(i=0;i<size;++i){
for(j=0;j<=bucket_position[i];++j){
array[k] = buckets[i][j];
++k;
}
}
//Do insertion sort over the array
insertion(array,n);
}
int main(){
int array[5] = {24354,95023,439052,934851};
int n = 5;
bucket(array,n);
return 0;
}
程序输出是分段错误而不是排序数组。
【问题讨论】:
-
调试器........
-
程序收到信号SIGSEGV,分段错误。存储桶中的 0x0804868b (array=0xbffff1a8, n=5) at test.c:41 41 buckets[pos][bucket_position[pos]] = array[i]; (gdb)
-
由于这发生在
i <= 0 < n的循环中,您应该查看pos,这可能超出了范围。 (您可以在 gdb 中使用print pos或仅使用p pos。) -
@Ruan 感谢调试。您应该在该行上设置断点并检查索引“pos”和“i”的值。
-
您创建了 186970 个存储桶,每个存储桶可容纳 934851 个整数,所有这些都用于对大小为 5 的数组进行排序。有点矫枉过正,你不觉得吗?
:)