2014-04-10 2 views
1

두 개의 동적 배열을 사용하여 원래 배열을 정렬하는 프로그램을 작성했습니다. 하나는 왼쪽, 다른 하나는 오른쪽에 대한 정렬입니다.동적 배열이 올바르게 초기화되지 않았습니다.

그러나 동적 배열은 23 번째 줄과 28 번째 줄에서 원래 배열을받지 못합니다 (배열 전체에서 cout 메서드에 의해 입증 됨). 이들은 비어 있거나 범위를 벗어난 요소를 포함합니다. 따라서 프로그램이 전체적으로 작동하지 않습니다. 내 질문은 초기화 자체에 문제가 있습니까? 아니면 18-19 행의 선언과 함께 있습니까? 필자는 개인적으로 선언문과 함께 있다고 믿지만 동적 배열의 경우처럼 크기를 너무 많이 사용하고 싶지는 않습니다. 적절한 테스트를위한 모든 방법을 포함했지만, 불필요한 것으로 판단되는 경우이 질문을 편집합니다. 당신의 도움에 미리 감사드립니다.

#include "stdafx.h" 
#include <iostream> 
using namespace std; 

void Merge(int *array, int left, int middle, int right) 
{ 
int * LArray; 
int * RArray; 
int counter = left;//This counter is used as a marker for the main array. 
int mid = middle; 

cout<<"Left " << left << "middle: "<< middle << " right: " << right<<endl; 

LArray = new int[middle-left + 1]; 
RArray = new int[right]; 

/*Initializes LArray*/ 
for (int i = left; i < middle - left + 1; i++) 
{ 
    LArray[i] = array[i]; 
} 

/*Initializes RArray*/ 
int temp = 0; 
for (int i = middle; i < right; i++) 
{ 
    RArray[temp] = array[i]; 
    temp++; 
} 

/*Prints out LArray*/ 
cout<<"LARRAY: "; 
for (int i = left; i < middle- left + 1; i++) 
{ 
    cout<<LArray[i]<< " "; 
} 

/*Prints out RArray*/ 
cout<<endl<<"RARRY: "; 
temp = 0; 
for (int i = middle; i < right; i++) 
{ 
    temp = 0; 
    cout<<RArray[temp]<< " "; 
    temp++; 
} 
cout<<endl; 

while (left <= middle && mid <= right) 
{ 
    /*This if statement checks if the number in the left array is smaller than the number in the right array*/ 
    if (LArray[left] < RArray[right]) 
    { 
     array[counter] = LArray[left]; 
     left++; 
     counter++; 
     cout<<"First if: array[counter]: "<< array[counter]<<" LArray[left]" << LArray[left]<<" left: "<< left<<" counter : "<< counter<<endl; 
    } 
    /*This else statement checks if the number in the right array is smaller than the number in the left array*/ 
    else 
    { 
     array[counter] = RArray[right]; 
     mid++; 
     counter++; 
     cout<<" First else: array[counter]: "<< array[counter] << " RArray[right] "<< RArray[right]<<" mid: "<< mid<<" counter : "<< counter<<endl; 
    } 
} 
/*If RArray is completed, check this one for any remaining elements.*/ 
while (left <= middle) 
{ 
    array[counter] = LArray[left]; 
    left++; 
    counter++; 
    cout<<" First while: array[counter]: "<< array[counter]<<" LArray[left]" << LArray[left]<<" left: "<< left<<" counter : "<< counter<<endl; 
} 

/*If LArray is completed, check this one for any remaining elements.*/ 
while (mid <= right) 
{ 
    array[counter] = RArray[right]; 
    mid++; 
    counter++; 
    cout<<" Second while: array[counter]: "<< array[counter] << " RArray[right] "<< RArray[right]<<" mid: "<< mid<<" counter : "<< counter<<endl; 
} 

delete [] LArray; 
delete [] RArray; 

} 


void MergeSort(int *array,int left, int right) 
{ 
if (left < right) 
{ 
    int middle = (left + right)/2; 
    MergeSort(array, left, middle); 
    MergeSort(array, middle + 1, right); 
    Merge(array, left, middle, right); 
} 
}; 

/*Checks if the array listed is sorted by looping through and checking if the current number is smaller than the previous.*/ 
bool IsSorted(int* array, unsigned long long size) 
{ 

for (int i = 0; i < size; i++) 
{ 
    cout<<array[i]<< " "; 
} 
cout<<endl; 
for (int i = 1; i < size; i++) 
{ 
    if (array[i] < array[i-1]) 
     return false; 
} 
return true; 
} 

int _tmain(int argc, _TCHAR* argv[]) 
{ 
int array[8] = {5, 2, 4, 7, 1, 3, 2, 6}; 
MergeSort(array, 0, 8); 

bool check = IsSorted(array, 8); 

if (check) 
    cout<<"It is sorted!"; 
else 
    cout<<"It is not sorted!"; 
return 0; 
} 
+0

'std :: vector'를 사용할 수없는 이유는 무엇입니까? – Massa

+0

@Massa 글쎄, 그는 두 개의 배열을 사용하여 MergeSort를 가르쳐 주었다. 그러나, 그가 그걸로 괜찮을 지 확신이 서지 않았기 때문에 나는 그에게 이메일을 보냈다. 그가 그걸로 괜찮다고 가정하면, 어떻게 도움이 될지 설명해 주시겠습니까? 그게 어리석은 질문이라면 사과하지만 std :: vector에 익숙하지 않습니다. – user3280790

+0

[여기] (http://en.cppreference.com/w/cpp/container/vector)를보십시오. 'std :: vector'는 단지 동적이며 동적으로 할당 된 멋진 배열입니다. 배열'LArray'와'RArray'를 할당하고 할당 해제하는 것에 대해 걱정할 필요가 없을 것입니다. 그러나 두번째로 보면, 이것은 당신의 문제는 아닌 것 같습니다. 내일 아침에 살펴볼 것입니다. 그때까지 아무도 대답하지 않았다면! – Massa

답변

1

병합 정렬의 개념은 배열을 두 개의 반쪽으로 재귀 적으로 분할하고 두 개의 반쪽을 정렬 한 다음 다시 병합하는 것입니다. 여기

내가 코드를 잘못 볼 수있는 것들 :

알고리즘과 문제가되지 않습니다

코드 불확실성 : 당신이 그것을 할당하고 있기 때문에

왼쪽 배열, 필요 이상으로 항상 큰 중간 요소를 가져 와서 초기화하십시오.

오른쪽 배열을 두 번 초기화합니다. 알고리즘과

실제 문제 : 당신은 제대로 카운터를 초기화하지 않을

, 그것은 항상 '0'으로 설정되고, 그래서 상관없이 호출 스택에 얼마나 깊이, 당신은 항상 설정되지 않은 요소 0 중간을 통해 왼쪽과 오른쪽 사이의 범위 대신 정렬 된 배열이됩니다.

당신은 권리가 그것을 할당하기 때문에 항상 옳다 배열의 요소의 수보다 큰 것 인수 바로 ... (가) 오른쪽 배열에 인덱스에 노력하고 - 중간 요소를.

또한 MergeSort 기능에 오류가 있습니다. 당신은 결코 실제로 [우측]이 RArray에 추가되지 않습니다 병합 기능 배열 이후 중간 요소를 정렬되지 않은, 그래서 첫 번째 재귀 호출을 정렬 할 것입니다, 당신은 중간 + 1에 전달하는 두 번째 재귀 호출에을 입력하면 정렬되지 않습니다.

+0

오류를 지적 해 주셔서 감사합니다.MergeSort는 현재 잘 분류되어 있습니다. 지금도 여전히 매우 큰 양수 및 음수를 표시합니다. 이는 여전히 범위를 벗어나는 신호입니다. 여기에 문제가 있습니다 .- 지금 바보처럼 들릴지 모르겠지만, 지금 제 코드를 가지고 있고 (당신이 말한 것을 반영하도록 위의 코드를 업데이트하려고합니다), RArray는 항상 비어 있습니다. , 전화를 걸면 높은 숫자를 알려줍니다. 오른쪽 중간이 보통 0이기 때문에 대개 초기화되지 않습니다. RArray를 바로 초기화해야한다고 생각합니까? – user3280790

+0

그래서 이제 LArray의 크기는 정확하지만 RArray의 크기는 정확하지 않습니다! 실제로 파생 값을 여러 번 사용하는 경우 (예 : ** middle-left + 1 **) 변수를 저장하여 매번 계산할 필요가 없도록해야합니다. 또한 LArray 나 RArray가 크기가 0이 아닌지 확인해야합니다. 배열에 0 요소를 할당하려고하면 문제가 발생할 것입니다. LArray를 잘못 초기화하면 일반적으로 경계를 넘어 값을 입력하게됩니다. RArray를 초기화하는 방법은 정확합니다. – Malketh

+0

while 루프도 여전히 올바르지 않습니다. LArray와 RArray는 모두 배열보다 작으므로 ** left ** 및 ** right **를 사용하여 인덱스 할 수 없습니다. RArray를 초기화 할 때와 마찬가지로 0부터 시작하는 다른 변수를 사용하십시오. – Malketh

관련 문제