2010-11-23 3 views
2

좋아, 그래서 int로 구성된 배열에 몇 가지 정렬 알고리즘을 실행하고 각 하나 걸리는 시간을 추적하기로되어있는 간단한 C + + 프로그램이 있습니다. 꽤 기본적인,하지만 문제가 생겼어.세그 폴트의 원인은 무엇인지는 알지만 그 이유는 무엇입니까?

프로그램이 처음 시작될 때 배열에서 원하는 항목 수를 묻습니다. 내 임무는 100 개 항목에서 750000까지 특정 길이로 배열을 설정하는 것입니다. 최대 600000까지 포함하여 많은 값을 처리 할 것입니다. 그러나 750000을 시도하면 즉시 segfaults가됩니다. 여기 저기에있는 몇 가지 소리가 나에게 네 번째 배열 (모두 같은 길이)이 초기화 될 때 오류가 발생한다는 것을 알게되었습니다. 이상한 것은 OS에서만 발생한다는 것입니다. 내 학교에서 아무 문제 없어.

난 그냥 참조의 전체 코드가 포함되어 있습니다. (우리 학교는 레드햇을 사용하는 반면 그 유용 경우 난 최신 우분투에 확실하지 않다)하지만 세그먼트 폴트 라인 (27)에서 발생

int array1[num], array2[num], array3[num], array4[num]; // initialize arrays 

I 각각의 배열을 별도의 줄에 초기화하고 그 사이에 머리를 집어 넣었 기 때문에 이것을 알 수 있습니다. array1, 2 및 3이 초기화되면 segfaults가 발생합니다. 다시 이것은 어레이가 약 600000 정도 이상일 때만 발생합니다. 아무것도 덜 잘 작동합니다.

전체 코드 : 어떤 도움을 주시면 더 좋구요

#include <iostream> 
#include <cstdlib> 
#include <ctime> 

using namespace std; 

void insertionSort(int array[], int size); 
void bubbleSort(int array[], int size); 
void mergeSort(int array[], int first, int last, int size); 
void quickSort(int array[], int size); 

int main() 
{ 

    cout << endl << endl << "\t\t**** Extra Credit Assignment- Sorting ****" << endl << endl << endl; 
    cout << "Enter the number of items to sort: "; 
    int num; 
    cin >> num; 
    while(cin.fail()) // while cin does not recieve an integer 
    { 
     cin.clear(); 
     cin.ignore(1000, '\n'); 
     cout << "Invalid entry. Try again: "; // try again 
     cin >> num; 
    } 

    int array1[num], array2[num], array3[num], array4[num]; // initialize arrays 

    int randNum, sizeOfArray = sizeof(array1)/sizeof(array1[0]); // random number, size of the arrays 
    srand(time(NULL)); // random seed (used with rand()) 

    for(int i = 0; i < sizeOfArray; i++) // traverse through the array 
    { 
     randNum = rand() % 2147483647+1; // establish random number (from 1 to 2147483647) 
     array1[i] = array2[i] = array3[i] = array3[i] = randNum; // set randNum to all arrays at current index 
    } 

    time_t beginTime, endTime; 
    double elapsedTime; 

    cout << endl << "Elapsed time:" << endl << "\tInsertion Sort-\t"; 

    time(&beginTime); 
    insertionSort(array1, sizeOfArray); 
    time(&endTime); 

    elapsedTime = difftime(endTime, beginTime); 
    cout << elapsedTime << " seconds" << endl << "\tBubble Sort-\t"; 

    time(&beginTime); 
    bubbleSort(array2, sizeOfArray); 
    time(&endTime); 

    elapsedTime = difftime(endTime, beginTime); 
    cout << elapsedTime << " seconds" << endl << "\tMerge Sort-\t"; 

    time(&beginTime); 
    mergeSort(array3, 0, sizeOfArray-1, sizeOfArray); 
    time(&endTime); 

    elapsedTime = difftime(endTime, beginTime); 
    cout << elapsedTime << " seconds"<< endl; 





/* ********************* TESTING ************************* 
// ******************************************************* 

    cout << "Insertion->Unsorted:\t"; 
    for(int i = 0; i < sizeOfArray; i++) 
    { 
     cout << array1[i] << " "; 
    } 
    cout << endl; 

    insertionSort(array1, sizeOfArray); 

    cout << "Insertion->Sorted:\t"; 
    for(int i = 0; i < sizeOfArray; i++) 
    { 
     cout << array1[i] << " "; 
    } 
    cout << endl; 




    cout << "Bubble->Unsorted:\t"; 
    for(int i = 0; i < sizeOfArray; i++) 
    { 
     cout << array2[i] << " "; 
    } 
    cout << endl; 

    bubbleSort(array2, sizeOfArray); 

    cout << "Bubble->Sorted:\t\t"; 
    for(int i = 0; i < sizeOfArray; i++) 
    { 
     cout << array2[i] << " "; 
    } 
    cout << endl; 




    cout << "Merge->Unsorted:\t"; 
    for(int i = 0; i < sizeOfArray; i++) 
    { 
     cout << array3[i] << " "; 
    } 
    cout << endl; 

    mergeSort(array3, 0, sizeOfArray-1, sizeOfArray); 

    cout << "Merge->Sorted:\t\t"; 
    for(int i = 0; i < sizeOfArray; i++) 
    { 
     cout << array3[i] << " "; 
    } 
    cout << endl; */ 

    return 0; 
} 

void insertionSort(int array[], int size) 
{ 
    for(int i = 1; i < size; i++) 
    { 
     int item = array[i], index = i; 
     while(index > 0 && array[index-1] > item) 
     { 
      array[index] = array[index-1]; 
      index--; 
     } 
     array[index] = item; 
    } 
} 

void bubbleSort(int array[], int size) 
{ 
    bool sorted = false; 
    for(int i = 1; i < size && !sorted; i++) 
    { 
     sorted = true; 
     for(int i2 = 0; i2 < size-i; i2++) 
     { 
      int nextI = i2+1; 
      if(array[i2] > array[nextI]) 
      { 
       swap(array[i2], array[nextI]); 
       sorted = false; 
      } 
     } 
    } 
} 

void merge(int array[], int first, int mid, int last, int size) 
{ 
    int tempArray[size]; 
    int first1 = first, first2 = mid+1; 
    int last1 = mid, last2 = last; 
    int index = first1; 

    while(first1 <= last1 && first2 <= last2) 
    { 
     if(array[first1] < array[first2]) 
     { 
      tempArray[index] = array[first1]; 
      first1++; 
     } 
     else 
     { 
      tempArray[index] = array[first2]; 
      first2++; 
     } 
     index++; 
    } 
    while(first1 <= last1) 
    { 
     tempArray[index] = array[first1]; 
     first1++; 
     index++; 
    } 
    while(first2 <= last2) 
    { 
     tempArray[index] = array[first2]; 
     first2++; 
     index++; 
    } 

    for(index = first; index <= last; index++) 
    { 
     array[index] = tempArray[index]; 
    } 
} 

void mergeSort(int array[], int first, int last, int size) 
{ 
    if(first < last) 
    { 
     int mid = (first+last)/2; 
     mergeSort(array, first, mid, size); 
     mergeSort(array, mid+1, last, size); 
     merge(array, first, mid, last, size); 
    } 
} 

. 시스템에 메모리 제한이 있습니까? 나는 정말로 생각하지 못한다.

+0

그것을 올릴 수 참조하십시오 : http://stackoverflow.com/questions/408670/stack-static-and-heap-in-c –

답변

2

다른 사람들이 지적했듯이 SEGV는 스택 오버플로가 발생합니다. 우분투 시스템에서 발생하는 이유는 학교의 레드햇 시스템이 아니라 기본 스택 크기의 차이 때문일 수 있습니다.

기본 스택 크기를 ulimit -s으로 변경할 수 있습니다. 추가 인수없이 현재 스택 크기가 킬로바이트 단위로 인쇄됩니다. 예를 들어, 내 컴퓨터에서는 8192 또는 8 메가 바이트를 인쇄합니다. 나는 아마 ... (당신이 가지고있는 것처럼) 12메가바이트이 ​​필요합니다 그래서 4 개와 같은 배열, 스택 공간 3메가바이트 (INT 당 4 바이트)에 대해 필요합니다 ulimit -s 16384

750000 int 배열로 16메가바이트에

+0

감사합니다! 완벽하게 일했습니다. 나는 새로운 터미널을 열 때마다 그것을 설정해야한다는 것을 알아 차렸다. 16 메가 바이트의 스택 크기를 영구적으로 설정하는 방법은 무엇입니까? – JoeC

+2

이것은 문제에 대한 확장 가능한 해결책이 아니므로 올바르게 작동하도록 코드를 수정하십시오. –

+0

@JoeC, .bashrc 또는 다른 쉘 시작 파일에 ulimit을 넣을 수 있습니다 (사용하는 쉘에 따라 다름) –

6

당신은 고정 된 제한 크기가 스택에 같은 큰 배열을 할당 할 수 없습니다, 시도 :

int* array1 = new int[num]; 
+0

감사합니다. 즉, 나머지 배열은 실제 배열 대신 포인터를 사용하도록 편집해야합니다. ;/어떻게 3 개의 큰 배열이 할당되었지만 네 번째 배열에서 실패합니까? 제한을 연장 할 수있는 방법이 있습니까? – JoeC

+0

배열 앞에 static 키워드를 추가하기 만하면됩니다. 그러면 메모리가 힙으로 이동합니다. –

+0

아니요, 모든 int *를 배열로 취급 할 수 있습니다.시도 해봐! –

2

당신은 스택에 매우 큰 배열을 할당 한 당신은 스택 오버 플로우를하고 있습니다. 새로 만들거나 정적으로 만들면 힙에 할당되어 실패하지 않게됩니다.

+0

나는이 아이디어가 마음에 들지만 이제는 ExCred.cpp : 28 : error : 'array1'의 저장소 크기가 일정하지 않다. " num 대신 const int를 선언했지만 오류가 발생합니다. 어떤 아이디어? – JoeC

1

스택이 무한한 리소스가 아니기 때문입니다. int x[big_honkin_number]을 수행하면 해당 배열의 스택에 충분한 공간을 할당하려고 시도합니다.

일반적으로 코드를 컴파일/링크하여 더 많은 스택을 제공 할 수 있지만 더 나은 해결책은 동적 메모리 할당 (즉, new)을 사용하는 것입니다.

관련 문제