好的,我遇到了一个奇怪的问题。我正在实施一种称为eratosthenes筛的算法。我有一个函数primeArray_r
递归地通过我生成的数组,然后一旦它到达结束,它在堆上创建一个新的数组,然后开始填充它,因为它下降通过堆栈,最后将指针返回到数组的开头。如果您想知道为什么我直接递增指针,那么这是分配的要求。我在运行时遇到问题,但这取决于我使用的环境。
在Windows中,它似乎在没有警告的情况下爆炸,有时在重复完全相同的序列时。在Ubuntu Linux中,它非常奇怪。它有点稳定,如果它工作一次,它会在同一个输入上多次工作,但它会根据输入而失败。例如,我的裸机安装,Ubuntu 14.04 64位程序将崩溃,如果上限是5,9,13,17 ...或任何数字(N * 4)+1,在我的虚拟安装, Lubuntu 13.10 32位,如果上限为2,4,6,8 ......或任何数字N * 2,它将崩溃。错误消息基本相同:
Program5.1: malloc.c:2372: sysmalloc: Assertion `(old_top == (((mbinptr) (((char *) &((av)->bins[((1) - 1) * 2])) - __builtin_offsetof (struct malloc_chunk, fd)))) && old_size == 0) || ((unsigned long) (old_size) >= (unsigned long)((((__builtin_offsetof (struct malloc_chunk, fd_nextsize))+((2 *(sizeof(size_t))) - 1)) & ~((2 *(sizeof(size_t))) - 1))) && ((old_top)->size & 0x1) && ((unsigned long) old_end & pagemask) == 0)' failed.
Aborted (core dumped)
唯一的区别是线路编号,Lubuntu 13.10中的malloc.c.2369和Ubuntu 14.04中的2372
似乎是我在第116行的内存分配期间导致了某种崩溃:
primeArray = new int[primeCount];
我想知道这是否是我的错误,或者我是否在递归堆栈末尾分配内存时发现了一些错误
#include<iostream>
#include <math.h>
using namespace std;
int* makeArray(int);
int firstZero (int*);
void circleCross(int*, int*, int);
void circleAll(int*, int*);
int* primeArray(int*, int*, int&, int);
int* primeArray_r(int*, int*, int*, int&, int);
int main(){
//display a title
cout << "The Sieve of Eratosthenes" << endl;
cout << "gives you all the primes you want!" << endl;
cout << "(in the range you specify...)" << endl;
//ask the user to specify a range of positive numbers
char repeat;
int low;
int high;
int size;
do{
do{
low = 0;
high = 0;
while (low < 1){
cout << "Give me the lower bound" << endl;
cin >> low;
}
while (high < 1){
cout << "Give me the upper bound" << endl;
cin >> high;
}
}while (low > high);
size = high + 1;
int* array = makeArray(size);
int *end = array + size;
int ix;
double root = sqrt(high);
do{
ix = firstZero(array);
if (ix <= root)
circleCross(array, end, ix);
}while ( ix < root);
circleAll(array, end);
array += low;
cout << "Found all the primes!" << endl;
int primeCount = 0;
int* arrayPrime = primeArray(array, end, primeCount, low);
cout << "Here's your primes!" << endl;
int *primeEnd = arrayPrime + primeCount;
while(arrayPrime < primeEnd){
cout << *arrayPrime << endl;
++arrayPrime;
}
cout << "Enter 'y' to go or any other character to stop" << endl;
cin >> repeat;
} while(repeat == 'y');
return 0;
}
int* makeArray( int size){
int *array;
array = new int[size];
int *firstAddress = array;
*array = -1;
*(++array) = -1;
int *end = firstAddress + size;
while (array < end){*(++array) = 0;}
return firstAddress;
}
int firstZero ( int* array){
int *ix;
for (ix = array; (*ix); ++ix);
int zero = ix - array;
return zero;
}
void circleCross( int* array, int *end, int factor){
array += factor;
*array = 1;
array += factor;
while(array < end){
*array = -1;
array += factor;
}
}
void circleAll( int* array, int *end){
while (array < end){
if (*array==0)
*array=1;
++array;
}
}
int* primeArray( int* array, int *end, int &primeCount, int low){
primeCount=0;
int *beginning = array;
int *primeArray = primeArray_r(array, beginning, end, primeCount, low);
return primeArray;
}
int* primeArray_r(int * array, int * beginning, int *end, int &primeCount, int low){
int *primeArray;
if (array == end){
primeArray = new int[primeCount];
primeArray += primeCount;
}
else{
if (*array == 1){
int position = primeCount;
++primeCount;
primeArray = primeArray_r((array+1), beginning, end, primeCount, low);
--primeArray;
*primeArray = array - beginning + low;
}
else{
primeArray = primeArray_r((array+1), beginning, end, primeCount, low);
}
}
return primeArray;
}
答案 0 :(得分:0)
在makeArray()中,您在数组(while (array < end){*(++array) = 0;}
)之后写入0,这会创建未定义的行为。所以这很可能是你崩溃的原因,因为这也与分配内存有关。