์ ๋ ฌ ์๊ณ ๋ฆฌ์ฆ์ด๋ n๊ฐ์ ์ซ์๊ฐ ์ฃผ์ด์ก์ ๋, ์ด๋ฅผ ์ฌ์ฉ์๊ฐ ์ง์ ํ ๊ธฐ์ค์ ๋ฐ๋ผ ์ ๋ ฌํ๋ ์๊ณ ๋ฆฌ์ฆ์ ๋ปํ๋ค.
์ง๊ธ๋ถํฐ ์ด๋ค ์๊ณ ๋ฆฌ์ฆ์ด ์๋์ง ์ดํด๋ณด๋๋ก ํ์.
๋น๊ต ์ ๋ ฌ(comparison sort)
๋น๊ต ์ ๋ ฌ์ ๋ฐฐ์ด์ ์์ ์ ๊ฐ์ ๋น๊ต๋ฅผ ๊ธฐ๋ฐ์ผ๋ก ์ ๋ ฌํ๋ ์๊ณ ๋ฆฌ์ฆ์ด๋ค.
๊ฐ์ฅ ์ฝ๊ฒ ์๊ฐํ ์ ์๋ ์๊ณ ๋ฆฌ์ฆ์ด์ O(nlogn)์ด๋ผ๋ ์๊ฐ ํ๊ณ๋ฅผ ๋์ด์์ง ๋ชปํ๋ค.
์ด๋ฌํ ๋น๊ต ์ ๋ ฌ์ ์ข ๋ฅ๋ก์จ ์ ํ ์ ๋ ฌ(Selection Sort), ์ฝ์ ์ ๋ ฌ(Insertion Sort), ํ ์ ๋ ฌ(Heap Sort), ํฉ๋ณ ์ ๋ ฌ(Merge Sort), ํต ์ ๋ ฌ(Quick Sort)์ด ์๋ค.
์ ํ ์ ๋ ฌ
์ ์ผ ๋จผ์ ์ ํ ์ ๋ ฌ์ด๋?
๋ฐฐ์ด์์ ์์ง ์ ๋ ฌ๋์ง ์์ ๋ถ๋ถ์์ ์ต์๊ฐ์ ์ ํํ์ฌ ์ ๋ ฌ๋ ๋ถ๋ถ์ ๋ฐ๋ก ์ค๋ฅธ์ชฝ ์์์ ๊ตํํ๋ ์ ๋ ฌ ์๊ณ ๋ฆฌ์ฆ์ ์๋ฏธํ๋ค.
๊ทธ๋ฆผ๊ณผ ๊ฐ์ด ์ธ๋ฑ์ค(i)๋ฅผ ํ๋์ฉ ์ฆ๊ฐ์ํค๋ฉฐ ํ์์ ํ๋ค.
๋ ธ๋์ ๋ฒ์์์ ์ต์๊ฐ์ ์ฐพ๊ณ ๊ทธ ๊ฐ์ ์ ๋ ฌ๋ ๋ถ๋ถ์ ์ ์ผ ์ค๋ฅธ์ชฝ์ ๋๋ค.
๋ค์์ ์ฝ์ ์ ๋ ฌ์ ๊ดํ ์ฝ๋ ์์์ด๋ค.
import java.lang.Comparable;
public class Selection {
public static void sort(Comparable[] a) {
// ์ ๋ ฌํ ๋ฐฐ์ด์ ๊ธธ์ด
int N = a.length;
for(int i=0; i<N; i++) {
// ์ต์๊ฐ์ ์ฐพ๊ธฐ ์์
int min = i;
// ๊ทธ๋ฆผ์์ ๋
ธ๋์ ๋ถ๋ถ์ ํด๋น
// ์ต์๊ฐ์ ์ฐพ์ -> isLess ๋ฉ์๋ ์ฌ์ฉ
for(int j=i+1, j<N; j++) {
if( isLess(a[j], a[min])) min = j;
}
// ์ต์๊ฐ๊ณผ ์ ๋ ฌ๋ ๋ถ๋ถ์ ๋งจ ์ค๋ฅธ์ชฝ ๋ถ๋ถ์ ๋ฐ๊ฟ
swap(a, i, min);
}
}
// ๋ ์์ ์ค ๋๊ฐ ๋ ์์ ์ง ๋น๊ตํ๋ ๋ฉ์๋
private static boolean isless(Comparable i, Compariable j) {
return (i.compareTo(j) < 0);
}
// ๋ฐฐ์ด์ ์์๋ฅผ ์๋ก ๊ตํ์ํค๋ ๋ฉ์๋
private static void swap(Comparable[] a, int i, int j) {
Comparable temp = a[i];
a[i] = a[j];
a[j] = temp;
}
}
์ ํ ์ ๋ ฌ์ ์ํ ์๊ฐ
์ ํ ์ ๋ ฌ์ ์ํ ์๊ฐ์ ํญ์ O(n^2)์ ์ํ ์๊ฐ์ด ์์๋๋ค.
๋ํ ์ ๋ ฅ์ ๋ฏผ๊ฐํ์ง ์๋ค๋ ํน์ง์ด ์๋ค.(Input Insensitive)
๋ฏผ๊ฐํ์ง ์๋ค๋ ๊ฒ์ ๋น๊ตํ์๊ฐ ํญ์ ๊ท ์ผํ๊ฒ ๋ณด์ฅ๋๊ธฐ ๋๋ฌธ์ด๋ค.
์ด์ ๋ํด ์๊ฐํด๋ณด๋ฉด ๋ฃจํ๊ฐ 1๋ฒ ์ํ๋ ๋๋ง๋ค ์ ๋ ฌ ์ ๋ ๋ถ๋ถ์์ ์ต์๊ฐ์ ์ฐพ์ ๊ฒ์ด๋ค.
์ด๋, n๊ฐ์ ์์์ค์์ min์ ์ฐพ๊ธฐ ์ํด n-1๋ฒ ๋น๊ตํ๊ณ ,
์ธ๋ฑ์ค๋ฅผ ํ ์นธ ์ด๋ ์ํจ ํ, n-1๊ฐ์ ์์ ์ค min์ ์ฐพ๊ธฐ ์ํด n-2๋ฒ ๋น๊ตํ ๊ฒ์ด๋ค.
๊ฒฐ๊ตญ, ์ ๋ ฌ์ํค๊ธฐ ์ํด์ (n-1) + (n-2) + (n-3) +... + 1๋ฒ๋งํผ ๋น๊ตํ๊ฒ ๋๋ค.
๊ทธ๋ ๊ธฐ์ ์ ๋ ฅ์ ์์ด ๋ฏผ๊ฐํ์ง ์๊ณ ์ํ ์๊ฐ์ด ํญ์ O(n^2)๋งํผ ์์๋๋ค.
์ฝ์ ์ ๋ ฌ(Insertion Sort)
์ฝ์ ์ ๋ ฌ์ด๋?
๋ฐฐ์ด์ด ์ ๋ ฌ๋ ๋ถ๋ถ๊ณผ ์ ๋ ฌ ์ ๋ ๋ถ๋ถ์ผ๋ก ๋๋๋ฉฐ, ์ ๋ ฌ ์ ๋ ๋ถ๋ถ์ ๊ฐ์ฅ ์ผ์ชฝ ์์๋ฅผ ์ ๋ ฌ๋ ๋ถ๋ถ์ ์ฝ์ ํ๋ฉฐ ์ ๋ ฌํ๋ค.
์ด์ ์ ์ ํ ์ ๋ ฌ๊ณผ์ ๊ณตํต์ ์ ์ ๋ ฌ๋ ๋ถ๋ถ๊ณผ ์ ๋ ฌ ์๋ ๋ถ๋ถ์ด ์๋ค๋ ๊ฒ์ด๋ค.
๋ค๋ง, ์ ๋ ฌ๋ ๋ถ๋ถ์ ์ ์ผ ์ค๋ฅธ์ชฝ์ ์ต์๊ฐ์ ์ถ๊ฐํ๋ ์ ํ ์ ๋ ฌ๊ณผ๋ ๋ฌ๋ฆฌ,
์ฝ์ ์ ๋ ฌ์ ์ ๋ ฌ๋ ๋ถ๋ถ์์ ๋ค์ด๊ฐ ์์น๋ฅผ ์ฐพ์ ๋ฃ๋๋ค.
๊ทธ๋ ๊ธฐ ๋๋ฌธ์ ์์๋ฅผ ์ฝ์ ํ ์ดํ,
์ ๋ ฌ๋ ๋ถ๋ถ์ ์์ ์๋ 1 ์ฆ๊ฐํ๊ณ ์ ๋ ฌ๋์ง ์์ ๋ถ๋ถ์ ์์ ์๋ 1 ๊ฐ์ํ๋ค๋ ํน์ง์ด ์๋ค.
๋ค์์ ์ฝ์ ์ ๋ ฌ์ ๊ด๋ จํ ์ฝ๋ ์์์ด๋ค.
import java.lang.Comaparable;
public class Insertion {
public static void sort(Comparable[] a) {
// ๋ฐฐ์ด ํฌ๊ธฐ ์ง์
int N = a.length;
for (int i=1; i<N; i++) {
// i๋ ํ์ฌ ์์์ ์ธ๋ฑ์ค์ด๋ค.
for(int j=i; j>0; j--) {
// ํ์ฌ ์์๋ฅผ ์ ๋ ฌ๋ ์ ๋ถ๋ถ์ ์ฝ์
ํ๋ค.
// ์ฆ, i๋ถํฐ 0๊น์ง์ ์ธ๋ฑ์ค๋ฅผ ํ์ํ๋ฉฐ ์ ์ ํ ์์น์ ๋ฃ๋๋ค.
if (isLess(a[j], a[j-1]) {
swap(a, j, j-1);
} else break;
}
}
}
}
์ฝ์ ์ ๋ ฌ์ ์ํ ์๊ฐ
์ฝ์ ์ ๋ ฌ์ ์๊ฐ ๋ณต์ก๋๋ ์ต์ ์ ๊ฒฝ์ฐ O(n), ์ต์ ์ ๊ฒฝ์ฐ O(n^2)์ด๋ค.
์ต์ ์ ๊ฒฝ์ฐ๋ ์ ๋ ฅ์ด ์ด๋ฏธ ์ ๋ ฌ๋ ๊ฒฝ์ฐ n-1๋ฒ๋ง ๋น๊ตํ๋ฉด ๋๋ฏ๋ก O(n)์ด๋ค.
๋ง์ฝ ์ ๋ ฅ์ด ์ญ์ผ๋ก ์ ๋ ฌ๋์๋ค๋ฉด, ์ ํ ์ ๋ ฌ๊ณผ ๊ฐ์ด ์ ๋ถ ๋น๊ตํด์ผ ํ๊ธฐ์ O(n^2)์ด ๋๋ฉฐ,
๋ฐ์ดํฐ๋ฅผ ๊ตํํ๋ ์๋ O(n^2)์ด ๋๋ค.
๊ทธ๋ฆฌ๊ณ , ํ๊ท ์ ์ธ ๊ฒฝ์ฐ๋ O(n^2)์ ๋ํ๋ด๋๋ฐ,
์ ์ต์ ์ ๊ฒฝ์ฐ์ ๊ฐ์ ์๊ฐ ๋ณต์ก๋๋ฅผ ๊ฐ์ง๋๊ฐํ๋ฉด...
์์๊ฐ ์ ๋ ฌ๋ ๋ถ๋ถ์ ์ต์ข ์ ์ผ๋ก ์ฝ์ ๋๋ ๋ถ๋ถ์ด ํ๊ท ์ ์ผ๋ก ์ ๋ ฌ๋ ๋ถ๋ถ์ ์ค๊ฐ ์ง์ ์ด๋ผ๊ณ ์๊ฐํ๊ธฐ ๋๋ฌธ์ด๋ค.
๊ทธ๋ ๊ธฐ์ ๊ธฐ์กด์ ์ต์ ์ ๊ฒฝ์ฐ์์ ๊ทธ๋ฅ 1/2์ ๊ณฑํ ๊ฒฐ๊ณผ ๋ฐ์ ์๋๊ณ ,
์๊ฐ ๋ณต์ก๋๋ ์์๋ฅผ ๊ณฑํด๋ดค์ ๋๊ฐ์ผ๋ฏ๋ก O(n^2)๋ฅผ ๋ํ๋ด๋ ๊ฒ์ด๋ค.
์ฝ์ ์ ๋ ฌ์ ์์ฉ
๊ทธ๋ ๋ค๋ฉด ์ค์ง์ ์ผ๋ก ์ฝ์ ์ ๋ ฌ์ ์ด๋ค ๊ฒฝ์ฐ์ ์ฌ์ฉํ๋ ๊ฒ ํจ์จ์ ์ธ๊ฐ?
์ด๋ฏธ ์ ๋ ฌ๋ ํ์ผ์ ๋ท๋ถ๋ถ์ ์๋์ ์ ๊ท ๋ฐ์ดํฐ๋ฅผ ์ถ๊ฐํ์ฌ ์ ๋ ฌํ๋ ๊ฒฝ์ฐ(์ ๋ ฅ์ด ๊ฑฐ์ ์ ๋ ฌ๋จ)
์ฐ์ํ ์ฑ๋ฅ์ ๋ณด์ธ๋ค.
๋ํ ์ ๋ ฅ ํฌ๊ธฐ๊ฐ ์์ ๊ฒฝ์ฐ์๋ ์ข์ ์ฑ๋ฅ์ ๋ณด์ธ๋ค.
์ํ ํธ์ถ์ ํ์ง ์๊ณ ํ๋ก๊ทธ๋จ์ด ๊ฐ๋จํ๊ธฐ ๋๋ฌธ์ด๋ค.
์ฝ์ ์ ๋ ฌ์ ํฉ๋ณ์ ๋ ฌ์ด๋ ํต ์ ๋ ฌ๊ณผ ํจ๊ป ์ฌ์ฉ๋์ด ์ค์ง์ ์ผ๋ก ์ฑ๋ฅ์ด ํฅ์๋๋ค.
(๋จ, ์ด๋ก ์ ์ธ ์ํ์๊ฐ์ ํฅ์๋์ง ์๋๋ค.)
ํ ์ ๋ ฌ(Heap Sort)
ํ ์ ๋ ฌ์ ํ ์๋ฃ๊ตฌ์กฐ๋ฅผ ์ด์ฉํ๋ ์ ๋ ฌ์ด๋ค.
ํ ์๋ฃ๊ตฌ์กฐ์ ๊ดํด ์๊ฐ๋์ง ์๋๋ค๋ฉด ๋ค์ ํฌ์คํ ์ ์ฐธ๊ณ ํ๊ธธ ๋ฐ๋๋ค.
[์๋ฃ๊ตฌ์กฐ] ์ฐ์ ์์ ํ(Priority Queue), ๊ทธ๋ฆฌ๊ณ ํ(Heap)
์ฐ์ ์์ ํ(Priority Queue) : ๊ฐ์ฅ ๋์ ์ฐ์ ์์๋ฅผ ๊ฐ์ง ํญ๋ชฉ์ ์ ๊ทผ๊ณผ ์ญ์ , ์์์ ์ฐ์ ์์๋ฅผ ๊ฐ์ง ํญ๋ชฉ ์ฝ์ ์ ์ง์ํ๋ ์๋ฃ๊ตฌ์กฐ์ด๋ค. ํ(Queue)๋ผ๊ณ ํจ์ ๋จผ์ ๋ค์ด์ค๋ ๋ฐ์ดํฐ๊ฐ ๋จผ์ ๋๊ฐ๋
devrepo.tistory.com
ํ ์ ๋ ฌ์ ๋ค์๊ณผ ๊ฐ์ ์์๋ก ์ ๋ ฌ์ ์ํํ๋ค.
1. ๋ฐฐ์ด์ ์ ์ฅ๋ ๋ฐ์ดํฐ์ ํค๋ฅผ ์ฐ์ ์์๋ก ํ๋ ์ต๋ ํ(Max Heap)์ ๊ตฌ์ฑํ๋ค.
2. ๋ฃจํธ์ ์ซ์๋ฅผ ํ์ ๊ฐ์ฅ ๋ง์ง๋ง ๋ ธ๋์ ์๋ ์ซ์์ ๊ตํํ๋ค.
3. ํ ํฌ๊ธฐ๋ฅผ 1 ๊ฐ์์ํจ๋ค.
์ด๋ ๋ง์ง๋ง์ผ๋ก ์ด๋ํ ์์๋ฅผ ๋ค์ ์ ๋ ฌ ์์ ๋ฐฐ์ ํ๊ธฐ ์ํจ์ด๋ค.
4. ๋ฃจํธ๋ก ์ด๋ํ ์ซ์๋ก ์ธํด ์๋ฐฐ๋ ํ์์ฑ์ downheap ์ฐ์ฐ์ผ๋ก ๋ณต์ํ๋ค.
5. ์ด ๊ณผ์ ์ ๋ฐ๋ณตํ์ฌ ์ ๋ ฌํ๋ค.
๋ค์์ Heap ์ ๋ ฌ๊ณผ ๊ด๋ จ๋ ์ฝ๋ ์์์ด๋ค.
import java.lang.Comparable;
public class Heap {
pulbic static void sort(Comparable[] a) {
// ํ ์ฌ์ด์ฆ ์ค์ (a[0]์ ํธ์๋ฅผ ์ํด ์ฌ์ฉ์ํจ)
int heapSize = a.length-1;
// ํ ๋ง๋ค๊ธฐ(์ํฅ์ ํ)
for(int i= heapSize/2; i>0; i--) {
downheap(a, i, heapSize);
}
// ํ ์ ๋ ฌ ์ํ
while(heapSize > 1) {
// a[1]๊ณผ ํ์ ๋ง์ง๋ง ํญ๋ชฉ๊ณผ ๊ตํ
swap(a, 1, heapSize--);
// ์๋ฐฐ๋ ํ์ ์์ฑ์ ๊ณ ์น๋ค.
downheap(a, 1, heapSize);
}
}
private static void downheap(Comparable[] a, int p, int heapSize) {
while(2*p <= heapSize) {
// s๋ ์ผ์ชฝ ์์ ์ธ๋ฑ์ค์ด๋ค.
int s = 2*p;
// ์ค๋ฅธ์ชฝ ์์์ด ๋ ํฐ ๊ฒฝ์ฐ
if (s < heapSize && isLess(a[s], a[s+1])) s++;
// ๋ถ๋ชจ๊ฐ ์์ ์น์๋ณด๋ค ํฌ๋ค๋ฉด ํ ์์ฑ ๋ง์กฑ
if (!isLess(a[p], a[s])) break;
// ํ ์์ฑ์ ๋ง์กฑํ์ง ์๋๋ค๋ฉด ๋ถ๋ชจ์ ์์ ์น์ ๊ตํ
swap(a, p, s);
// ์ด์ ์์ ์น์์ ์๋ฆฌ์ ๋ถ๋ชจ๊ฐ ์๊ฒ ํจ
p = s;
}
}
}
์ํฅ์ ํ์ ๋ง๋๋ ๊ณผ์ ์ด๋ downheap์ ๊ดํด์ ํท๊ฐ๋ฆฐ๋ค๋ฉด, ๊ผญ ์ด์ ํฌ์คํ ์ ์ฐธ๊ณ ํ๊ธธ ๋ฐ๋๋ค.
ํ ์ ๋ ฌ์ ์ํ ์๊ฐ
์ด ์ํ ์๊ฐ์ O(nlogn)์ด๋ค.
๊ทธ ์ด์ ๋ ๋จผ์ ์ํฅ์(Bottom-up) ๋ฐฉ์์ผ๋ก ํ์ ๊ตฌ์ฑํ๋ ๊ฒฝ์ฐ O(n) ์๊ฐ์ด ์์๋๊ณ ,
๋ฃจํธ์ ํ์ ๋ง์ง๋ง ๋ ธ๋๋ฅผ ๊ตํํ ํ, downheap์ ์ํํ๋ ๋ฐ ์์ด O(logn) ์๊ฐ์ด ์์๋๋ค.
๊ทธ๋ฆฌ๊ณ ๋ฃจํธ์ ํ์ ๋ง์ง๋ง ๋ ธ๋๋ฅผ ๊ตํํ๋ ํ์๋ n-1๋ฒ์ด ๋๋ฏ๋ก
O(logn) * (n-1)์ ์ํํด ์ฃผ์ด์ผ ํ๋ค.
๊ฒฐ๊ตญ ์ด ์ํ ์๊ฐ์ O(n) + (n-1) * O(logn) = O(nlogn)์ด ์์๋๋ค.
ํ ์ ๋ ฌ์ ์ด๋ ํ ์ ๋ ฅ์๋ ํญ์ O(nlogn) ์๊ฐ์ด ์์๋๋ค๋ ํน์ง์ด ์๋ค.
ํฉ๋ณ ์ ๋ ฌ(Merge Sort)
ํฉ๋ณ ์ ๋ ฌ์ด๋?
ํฌ๊ธฐ๊ฐ n์ธ ์ ๋ ฅ์ n/2 ํฌ๊ธฐ๋ก ๋ถํ ํ๊ณ , ๊ฐ๊ฐ์ ๋ํด ์ํ์ผ๋ก ํฉ๋ณ ์ ๋ ฌ์ ์ํํ ํ, 2๊ฐ์ ๊ฐ๊ฐ ์ ๋ ฌ๋ ๋ถ๋ถ์ ํฉ๋ณํ๋ ์ ๋ ฌ ์๊ณ ๋ฆฌ์ฆ์ ๋ปํ๋ค.
๐ค ์ด๋ ํฉ๋ณ(Merge)์ด๋?
2๊ฐ์ ๊ฐ๊ฐ ์ ๋ ฌ๋ ๋ฆฌ์คํธ๋ฅผ 1๊ฐ์ ์ ๋ ฌ๋ ๋ฆฌ์คํธ๋ก ๋ง๋๋ ๊ฒ์ด๋ค.
ํฉ๋ณ ์ ๋ ฌ์ ๋ถํ ์ ๋ณต(Divide-and-Conquer) ์๊ณ ๋ฆฌ์ฆ์ ํ์ฉํ ์๊ณ ๋ฆฌ์ฆ์ธ๋ฐ,
๋ถํ ์ ๋ณต์ด๋ ์ ๋ ฅ์ ๋ถํ ํ์ฌ ๋ถํ ๋ ์ ๋ ฅ ๊ฐ๊ฐ์ ๋ํด ๋ฌธ์ ๋ฅผ ์ํ์ผ๋ก ํด๊ฒฐํ ํ, ์ทจํฉํ์ฌ ๋ฌธ์ ๋ฅผ ํด๊ฒฐํ๋ ์๊ณ ๋ฆฌ์ฆ์ด๋ค.
ํฉ๋ณ ์ ๋ ฌ์ ์ฝ๋๋ก ์ดํด๋ณด์.
import java.lang.Comarable;
public class Merge {
private static void merge(Comaprable[] a, Comaparable[] b, int low, int mid, int high) {
int i = low, j = mid + 1;
// low~mid, mid+1~high ๋ ๋ฐฐ์ด์ ์์ ๋ฐฐ์ด b์ ํฉ๋ณํ๋ค.
for (int k = low, k<=high; k++) {
// ์ ๋ถ๋ถ์ด ๋จผ์ ์์ง๋ ๊ฒฝ์ฐ์ด๋ค.(i์ ์ด๊น๊ฐ = low)
// ์ด ๊ฒฝ์ฐ, j๊ฐ์ ๋ฃ๋๋ค.
if (i > mid) b[k] = a[j++];
// ๋ท ๋ถ๋ถ์ด ๋จผ์ ์์ง๋ ๊ฒฝ์ฐ์ด๋ค.(j์ ์ด๊น๊ฐ = mid+1)
else if (j > high) b[k] = a[i++];
// ๋ i์ j์ ๊ฐ์ ๋น๊ตํ๋ฉฐ ๊ฐ์ ๋ฃ๋๋ค.(์ด๋ ์ค์ง์ ์ผ๋ก ์ ๋ ฌ)
else if (isLess(a[j], a[i])) b[k] = a[j++];
else b[k] = a[i++];
}
// ์์ ๋ฐฐ์ด b์ ๊ฐ์ a์ ๊ฐ์ผ๋ก ์ฎ๊ธด๋ค.
for (int k = low; k<=high; k++) a[k] = b[k];
}
public static void sort(Comparable[] a, Comaparable[] b, int low, int high) {
if (high <= low) return;
// low์ high์ ์ค๊ฐ ๊ฐ์ธ mid ๊ฐ์ ์ค์ ํ๋ค.
int mid = low + (high - low) / 2;
// ๋๋์ด์ง mid ๊ฐ์ ๊ธฐ์ค์ผ๋ก sort๋ฅผ ์ํํ๋ค.
sort(a, b, low, mid);
sort(a, b, mid + 1, high);
merge(a, b, low ,mid, high);
}
public staic void sort(Comparable[] a) {
// ์ ์ฒด ๋ฐฐ์ด ๋ฒ์๋ฅผ ๊ธฐ์ค์ผ๋ก ์ ๋ ฌ์ ์ํํ๋ค.
Comaparable[] b = new Comparable[a.length];
sort(a, b, 0, a.length-1);
}
private static boolean isless(Comparable v, Comparable w) {
return (v.compareTo(w) < 0);
}
}
ํท๊ฐ๋ฆฌ๋๊น, ์ฝ๋์ ํ๋ฆ์ ๊ฐ์ด ์ดํด๋ณด์.
๋ ๋ฒ์งธ๋ก ๋์ค๋ sort ๋ฉ์๋๊ฐ ๋จผ์ ํธ์ถ๋๋ฉด ์ ๋ ฌ์ ์คํ๋๋ค.
์ด๋ ๋ฐฐ์ด a ์ ์ฒด๋ฅผ ์ ๋ ฌํ๋ ๋ฉ์๋๋ก, ๋ณด์กฐ ๋ฐฐ์ด b๋ฅผ ์์ฑํ๊ณ ,
์ฒซ ๋ฒ์งธ sort ๋ฉ์๋๋ฅผ ํธ์ถํ์ฌ ๋ฐฐ์ด์ ์ ์ฒด ๋ฒ์๋ฅผ ์ ๋ ฌํ๋ค.
์ฒซ ๋ฒ์งธ๋ก ๋์ค๋ sort ๋ฉ์๋๋ ๋ฐฐ์ด a์ ํน์ ๋ถ๋ถ์ ์ ๋ ฌํ๋ ๋ฉ์๋์ด๋ค.
low์ high ์ธ๋ฑ์ค๋ฅผ ์ด์ฉํ์ฌ ๋ฐฐ์ด์ ๋ถ๋ฆฌํ๊ณ , ์ฌ๊ท์ ์ผ๋ก ๋ถ๋ถ ๋ฐฐ์ด๋ก ์ ๋ ฌํ ํ, merge๋ฉ์๋๋ฅผ ํธ์ถํ์ฌ ํฉ๋ณํ๋ค.
merge๋ฉ์๋๋ ๋ฐฐ์ด a์ ์ผ๋ถ๋ถ์ ํฉ๋ณํ๋ ๋ฉ์๋์ด๋ค.
low๋ถํฐ mid๊น์ง ์ฒซ ๋ฒ์งธ ๋ถ๋ถ ๋ฐฐ์ด๊ณผ mid+1๋ถํฐ high๊น์ง์ ๋ ๋ฒ์งธ ๋ถ๋ถ ๋ฐฐ์ด์ ํฉ๋ณํ์ฌ ๋ณด์กฐ๋ฐฐ์ด b์ ์ ์ฅํ๋ค.
์ฆ, ๋ถํ ํ๊ณ (low~mid, mid+1~high) ๋ถํ ํ ๊ฐ์ ์ ๋ ฌํ๋ฉฐ ํฉ๋ณํ๋(merge) ๊ณผ์ ์ธ ๊ฒ์ด๋ค.
์ถ๊ฐ๋ก ํฉ๋ณ ์ ๋ ฌ์ ์์ ํ ์ ๋ ฌ์ด๋ผ๋ ํน์ง์ ๊ฐ์ง๊ณ ์๋ค.
์์ ํ ์ ๋ ฌ(Stable Sort) ์๊ณ ๋ฆฌ์ฆ์ ์ค๋ณต๋ ํค์ ๋ํด ์ ๋ ฅ์์ ์์ ์๋ ํค๊ฐ ์ ๋ ฌ ํ์๋ ์์ ์๋ ์๊ณ ๋ฆฌ์ฆ์ด๋ค.
๋ถ์์ ํ๋ค๋ฉด ๊ทธ ์์๊ฐ ๋ค๋ฐ๋๋ค.
ํต ์ ๋ ฌ(Quick Sort)
ํต ์ ๋ ฌ์ด๋?
์ ๋ ฅ์ ๋งจ ์ผ์ชฝ ์์(ํผ๋ฒ, Pivot)๋ฅผ ๊ธฐ์ค์ผ๋ก ํผ๋ฒ๋ณด๋ค ์์ ์์๋ค๊ณผ ํฐ ์์๋ค์ ๊ฐ๊ฐ ํผ๋ฒ์ ์ข์ฐ๋ก ๋ถํ ํ ํ, ์ข์ฐ ๋ถ๋ถ์ ๊ฐ๊ฐ ์ํ์ผ๋ก ์ ๋ ฌํ๋ค.
ํต ์ ๋ ฌ์ ๊ณผ์ ์ ๋ค์ ๊ทธ๋ฆผ์ ๋ณด๋ฉด ์ฝ๊ฒ ์ดํดํ ์ ์๋ค.
์ฆ, ์์ ๊ฐ์ด ํผ๋ฒ์ ์ค์ ํ๊ณ ๊ทธ ํผ๋ฒ๋ณด๋ค ์๊ฑฐ๋ ํฐ ๋ถ๋ถ์ผ๋ก ๋๋ ํ, ๋งจ ๋ง์ง๋ง์ผ๋ก ๋น๊ตํ ์์์๋ฆฌ์ ํผ๋ฒ์ด ์ด๋ํ๋ ํํ์ธ ๊ฒ์ด๋ค.
์ด๋ฌํ ๊ณผ์ ์ ๊ฐ๊ฐ์ ์์ ์์, ํฐ ์์ ์งํฉ์์ ๋ฐ๋ณต ์ํํ๋ ๊ฒ์ด ํต ์ ๋ ฌ์ ํต์ฌ์ด๋ค.
ํต์ ๋ ฌ์ ์ฝ๋๋ฅผ ์ดํด๋ณด์.
import java.lang.Comparable;
public class Quick {
public static void sort(Comparable[] a) {
// ์ ์ฒด ๋ฒ์ ์ ๋ ฌ ์ํ
sort(a, 0, a.length - 1);
}
private static void sort(Comparable[] a, int low, int high) {
// ์ข
๋ฃ ์กฐ๊ฑด
if(high <= low) return;
//
int j = partition(a, low, high);
sort(a, low, j-1);
sort(a, j+1, high);
}
private static int partition(Comparable[] a, int pivot, int high) {
// ํผ๋ฒ ์ธ๋ฑ์ค
int i = pivot;
// ๋งจ ๋ง์ง๋ง ๊ฐ ์ธ๋ฑ์ค ์ค์
int j = high+1;
// ํผ๋ฒ ๊ฐ ์ ๊ทผ
Comparable p = a[pivot];
while(true) {
// ํผ๋ฒ ๊ฐ๊ณผ ํผ๋ฒ ๋ค์ ๊ฐ์ผ๋ก๋ถํฐ ํ๋์ฉ ๋น๊ตํด ๋๊ฐ
// ์ฆ, ์์ชฝ ๋์์ ๋ถํฐ ๋น๊ตํด๋๊ฐ
// ํผ๋ฒ ๊ฐ๋ณด๋ค ํฐ์ง ์์์ง ๋น๊ต
// ์ด ๊ณผ์ ์ ํตํด i์ j๋ ๊ฐ๊ฐ ํผ๋ฒ๋ณด๋ค ์์ ๊ฐ, ํฐ ๊ฐ์ด ๋จ.
// ๋ง์ผ ๊ฐ ์ธ๋ฑ์ค ๊ฐ์ด ๋์ ๋๋ฌํ ๊ฒฝ์ฐ ์ข
๋ฃ
while(isLess(a[++i], p)) if (i == high) break;
while(isLess(p, a[--j])) if (j == pivot) break;
// ๋น๊ต์ง์ ์ด ๊ต์ฐจํ๊ฑฐ๋ ๊ฐ์์ง๋ ์๊ฐ ์ข
๋ฃ
if( i >= j ) break;
// i์ j ์ธ๋ฑ์ค ๊ฐ ๊ตํ(ํฐ ๊ฐ, ์์ ๊ฐ ๊ตํ)
swap(a, i, j);
}
// ๋ง์ง๋ง ํผ๋ฒ ๊ฐ๊ณผ ๊ตํ
swap(a, pivot, j);
return j;
}
}
ํต ์ ๋ ฌ์ ์ํ์๊ฐ
ํ๊ท , ์ต์ ์ ๊ฒฝ์ฐ๋ ํผ๋ฒ์ด ๋งค๋ฒ ์ ๋ ฅ์ 1/2์ฉ ๋ถํ ํ๋ ๊ฒฝ์ฐ์ด๋ฉฐ O(nlogn)์ด๋ค.
์ต์ ์ ๊ฒฝ์ฐ๋ ํผ๋ฒ์ด ๋งค๋ฒ ๊ฐ์ฅ ์๊ฑฐ๋ ๊ฐ์ฅ ํฐ ๊ฒฝ์ฐ๋ก ํผ๋ฒ๋ณด๋ค ์์ ๋ถ๋ถ์ด๋ ํฐ ๋ถ๋ถ์ด ์๋ ๊ฒฝ์ฐ์ด๋ค. : O(n^2)
ํต ์ ๋ ฌ์ ํ๊ท ์ ์ผ๋ก ๋น ๋ฅธ ์ํ ์๊ฐ์ ๊ฐ์ง๋ฉฐ, ๋ณด์กฐ ๋ฉ๋ชจ๋ฆฌ๋ฅผ ์ฌ์ฉํ์ง ์๋๋ค.
์ต์ ์ ๊ฒฝ์ฐ ์ํ ์๊ฐ์ด O(n^2)์ด๋ฏ๋ก ์ฑ๋ฅ ํฅ์ ๋ฐฉ๋ฒ๋ค์ ํตํด ์ด๋ฅผ ๋ณด์ํ ์ ์๋ค.
ํต ์ ๋ ฌ์ ์ฑ๋ฅ ํฅ์ ๋ฐฉ๋ฒ
ํต ์ ๋ ฌ์ ์ํ ํธ์ถ์ ์ฌ์ฉํ๋ฏ๋ก ์ ๋ ฅ์ด ์์ ํฌ๊ธฐ๊ฐ ๋์์ ๋, ์ฝ์ ์ ๋ ฌ์ ํธ์ถํ์ฌ ์ฑ๋ฅ์ ํฅ์ํ ์ ์๋ค.
๋ํ ํผ๋ฒ์ ๊ฐ์ ๋ฐ๋ผ ๋ถํ ๋๋ ๋ ์์ญ์ ํฌ๊ธฐ๊ฐ ๊ฒฐ์ ๋๋ฏ๋ก ํ์ชฝ์ด ๋๋ฌด ์ปค์ง๋ ๊ฒ์ ๋ฐฉ์งํ๊ธฐ ์ํด
Median-of-Three ๋ฐฉ๋ฒ์ ์ฌ์ฉํ ์ ์๋ค. ์ด๋ ๊ฐ์ฅ ์ผ์ชฝ(low), ์ค๊ฐ(mid), ๊ฐ์ฅ ์ค๋ฅธ์ชฝ(high) ์์ ์ค์์ ์ค๊ฐ ๊ฐ์ ํผ๋ฒ์ผ๋ก ์ฌ์ฉํ๋ ๋ฐฉ๋ฒ์ด๋ค.
๊ฐ๋ น 9๊ฐ์ ์์๋ฅผ ์ ํํ์ฌ ์ด๋ค์ 3๊ฐ์ฉ ํ๋์ ๊ทธ๋ฃน์ผ๋ก ์ฌ๊ฒจ, ๊ฐ ๊ทธ๋ฃน์์ ์ค๊ฐ ๊ฐ์ ์ ํํ๊ณ , ์ ํ๋ 3๊ฐ์ ์ค๊ฐ ๊ฐ ์ค์ ์ค๊ฐ๊ฐ์ ํผ๋ฒ์ผ๋ก ์ฌ์ฉํ๋ ๋ฐฉ์์ด๋ค.