-
반응형
0. 목차
1. 삽입정렬의 개념
정렬의 개념은 앞의 선택정렬에서 설명한것과 동일하다. (khu98.tistory.com/102?category=858723)
선택정렬에서 정렬을 하는법은, 정렬될 자리에 들어갈 원소를 선택한뒤, 교환을 하며 정렬을 하는거였다면,
삽입정렬은 해당 원소가 자기가 들어가야할 자리에 찾아가 삽입하며 정렬을 하는 방법이다.
선택정렬의 예와 동일한 예를 사용해보자.
배열에 5 1 4 7 2 가 있고, 이것을 오름차순으로 정렬하고싶다고 해보자. 편의상 인덱스를 1부터 시작한다고 가정하자.
이때, 맨 앞에있는 1번인덱스를 정렬되어있는 원소라고 생각한다.
인덱스 1 2 3 4 5 데이터 5 1 4 7 2 이제 2번인덱스에 있는 데이터인 1을 자기자리를 찾아 삽입시킬것이다.
오름차순 정렬이므로 5보다 앞에있어야 하므로 5와 1을 SWAP해준다.
STEP
1
RESULT인덱스 1 2 3 4 5 데이터 1 5 4 7 2 1과 5가 자기자리를 잘 찾았다.
다음으로 정렬되지않은 데이터중 3번인덱스에 있는 4의자리를 찾아줄것이다.
먼저 4의 앞에있는 5와 비교를 해보자. 4는 5보다 작으니 5보다 앞에 있어야 하므로 swap을 해주자.
STEP
2인덱스 1 2 3 4 5 데이터 1 4 5 7 2 그런뒤, 1과 비교를 했을때 , 4는 1보다 크니 1 뒤에 있는것이 맞다. 따라서 4가 있어야하는 위치에 잘 삽입이 된것이다.
STEP
2
RESULT인덱스 1 2 3 4 5 데이터 1 4 5 7 2 1 4 5 가 자기자리를 잘 찾았다.
다음으로 4번인덱스에 있는 7의 자리를 찾아주자. 앞에 정렬된 배열의 맨 뒤의 원소인 5와 비교를 해보았을때, 7이 더 크므로 바꿔주지 않아도 된다.
이때 5 앞에있는 원소들과는 비교를 안해도되는가???
이에 대한 답변은 앞에는 이미 정렬되어있는 배열이므로 자기보다 작은 원소를 만나면, 그 앞은 다 자신보다 작은 데이터라는 확신을 할 수 있으므로, 그 자리가 알맞은 자리라고 확신을 할 수 있게되는것이다.
STEP
3
RESULT인덱스 1 2 3 4 5 데이터 1 4 5 7 2 마지막으로 5번 인덱스에있는 2를 위치를 찾아 삽입시켜줄것이다.
먼저 정렬되어있는 제일 마지막 원소인 7과 비교해본다.
2가 7보다 작으니, 7보다 앞으로 가야하므로 2와 7을 SWAP해준다.
STEP
4-1인덱스 1 2 3 4 5 데이터 1 4 5 2 7 다음으론 2와 5를 비교해준다. 2가 5보다 작으므로 더 앞에있어야한다. 2와 5를 SWAP해주자.
STEP
4-2인덱스 1 2 3 4 5 데이터 1 4 2 5 7 다음으론 2와 4를 비교해준다. 2가 4보다 작으므로 더 앞에있어야 한다. 2와 4를 SWAP해주자.
STEP
4-3인덱스 1 2 3 4 5 데이터 1 2 4 5 7 다음으론 2와 1을 비교해준다. 2가 1보다 크므로, 2는 1의 뒤에 있어야 한다. 따라서 2의 자리를 찾은것이다.
STEP
4
RESULT인덱스 1 2 3 4 5 데이터 1 2 4 5 7 이렇게 5 1 4 7 2 의 원소가 모두 자기자리를 찾아 삽입되어 정렬되었다.
2.삽입정렬 과정 정리
- 먼저 맨 앞의 원소를 정렬된 원소라고 정한다.
- 정렬되지 않은 데이터들중 맨 앞에있는 원소를 선택한다.
- 정렬된 원소들을 맨 뒤에서부터 탐색한다.
- 자신의 앞에있는 원소가 자신보다 크다면, SWAP을 한뒤, 계속 탐색한다.
- 자신보다 작은원소를 만났다면 멈추고 2번으로 돌아간다.
- 마지막 원소까지 모두 2~5번 과정을 거친다.
3.삽입정렬 시간복잡도
N개의 데이터를 정렬한다고 한다면,
최악의 상황은 2번에서 선택한 원소가 매번 최솟값이라 정렬된 배열의 맨 앞까지 탐색을 하는경우이다. 따라서 맨 앞까지 탐색하는 시간 O(N)이 걸리는 로직을 N-1개의 원소가 반복해야하므로, 시간복잡도는 O(N2)이 된다.
4.삽입정렬 코드
#include<iostream> using namespace std; int main() { int arr[5] = { 5,1,4,7,2 }; int size = 5; int temp; cout << "정렬 전 :\t"; for (int i = 0; i < 5; i++) { cout << arr[i] << " "; } cout << "\n"; for (int i = 1; i < size ; i++) { for (int j = i ; j >= 1; j--) { if (arr[j - 1] > arr[j]) { int temp = arr[j - 1]; arr[j - 1] = arr[j]; arr[j] = temp; } //자기자리를 찾았으면, 더이상 탐색할 필요 x else { break; } } //중간결과 cout << i + 1 << "번째 결과 :\t"; for (int j = 0; j < 5; j++) { cout << arr[j] << " "; } cout << "\n"; } cout << "정렬 결과:\t"; for (int i = 0; i < 5; i++) { cout << arr[i] << " "; } cout << "\n"; return 0; }
반응형'알고리즘' 카테고리의 다른 글
[알고리즘] 최소공배수와 최대공약수 C++ (0) 2021.08.12 [알고리즘] 소수판별 알고리즘 C++ (0) 2021.08.11 [알고리즘] 퀵정렬 (Quick Sort) C++ (0) 2021.07.12 [알고리즘] 버블정렬 (Bubble Sort) C++ (0) 2021.05.06 [알고리즘] 선택정렬 (Selection Sort) C++ (0) 2021.05.03 댓글