Coding Test/Data Structure & algorithm

[์•Œ๊ณ ๋ฆฌ์ฆ˜] ์ •๋ ฌ (Sorting)

๊ต ๋ฏผ 2024. 9. 22. 17:43

๐Ÿ“์ •์˜

์ •๋ ฌ : ํŠน์ •ํ•œ ๊ธฐ์ค€์— ๋งž๊ฒŒ ์ˆœ์„œ๋Œ€๋กœ ๋‚˜์—ดํ•˜๋Š” ๋ฐฉ๋ฒ•

 

 

๐Ÿ“์ฃผ์š” ์ •๋ ฌ ์•Œ๊ณ ๋ฆฌ์ฆ˜ ( ๋กœ์ง & ์˜ˆ์‹œ ์ฝ”๋“œ )

 

1. ๋ฒ„๋ธ” ์ •๋ ฌ

 

โš™๏ธ ๋กœ์ง

  1. ์ธ์ ‘ํ•œ ๋‘ ์š”์†Œ๋ฅผ ๋น„๊ตํ•˜์—ฌ ํฌ๊ธฐ ์ˆœ์„œ๊ฐ€ ์ž˜๋ชป๋˜์–ด ์žˆ์„ ๊ฒฝ์šฐ, ์œ„์น˜๋ฅผ ๋ฐ”๊พผ๋‹ค
  2. ํ•œ ๋ฒˆ์˜ ํŒจ์Šค๊ฐ€ ๋๋‚˜๋ฉด ๊ฐ€์žฅ ํฐ ๊ฐ’์ด ๋งˆ์ง€๋ง‰์— ์œ„์น˜ํ•˜์—ฌ, ๋‚จ์€ ์š”์†Œ๋“ค์— ๋Œ€ํ•ด ๋ฐ˜๋ณตํ•œ๋‹ค.
  • ์‹œ๊ฐ„ ๋ณต์žก๋„ : O(n^2)
  • ๋‹จ์ˆœ, ๋น„ํšจ์œจ์  → ์ž‘์€ ๋ฐ์ดํ„ฐ์…‹์— ์ ํ•ฉํ•˜๋‹ค.

 

๐Ÿ“„ ์œ ํ˜• ์ดํ•ด ์ฝ”๋“œ

public class BubbleSort {
    public static void bubbleSort(int[] arr) {
        int n = arr.length;
        for (int i = 0; i < n - 1; i++) {
            for (int j = 0; j < n - i - 1; j++) {
                if (arr[j] > arr[j + 1]) {
                    // ์œ„์น˜ ๋ฐ”๊พธ๊ธฐ
                    int temp = arr[j];
                    arr[j] = arr[j + 1];
                    arr[j + 1] = temp;
                }
            }
        }
    }
}

 

 

2. ์„ ํƒ ์ •๋ ฌ

 

โš™๏ธ ๋กœ์ง

  1. ๋ฆฌ์ŠคํŠธ์—์„œ ๊ฐ€์žฅ ํฐ/์ž‘์€ ์š”์†Œ๋ฅผ ์ฐพ์•„ ์ฒซ ๋ฒˆ์งธ ์š”์†Œ์™€ ๊ตํ™˜ํ•œ๋‹ค.
  2. ์ดํ›„, ๊ทธ ๋‹ค์Œ ์š”์†Œ๋ถ€ํ„ฐ ๋‹ค์‹œ ๋ฆฌ์ŠคํŠธ์—์„œ ๊ฐ€์žฅ ํฐ/์ž‘์€ ๊ฐ’์„ ์ฐพ์•„ ๋‹ค์Œ ์š”์†Œ์™€ ๊ตํ™˜ํ•œ๋‹ค.
  3. ์œ„ ๊ณผ์ •์„ ๋ฐ˜๋ณตํ•˜๋ฉฐ ์ •๋ ฌ 
  • ์‹œ๊ฐ„ ๋ณต์žก๋„ : O(n^2)
  • ๋ฒ„๋ธ” ์ •๋ ฌ๋ณด๋‹ค ๋น„๊ต ํšŸ์ˆ˜๋Š” ์ ์ง€๋งŒ, ํšจ์œจ์„ฑ ↓
  • ์ œ์ž๋ฆฌ ์ •๋ ฌ์œผ๋กœ, ์ถ”๊ฐ€์ ์ธ ๋ฉ”๋ชจ๋ฆฌ ์‚ฌ์šฉ์ด ์ ๋‹ค.


๐Ÿ“„ ์œ ํ˜• ์ดํ•ด ์ฝ”๋“œ

public class SelectionSort {
    public static void selectionSort(int[] arr) {
        int n = arr.length;
        for (int i = 0; i < n - 1; i++) {
            int minIndex = i;
            for (int j = i + 1; j < n; j++) {
                if (arr[j] < arr[minIndex]) {
                    minIndex = j;
                }
            }
            // ์œ„์น˜ ๋ฐ”๊พธ๊ธฐ
            int temp = arr[i];
            arr[i] = arr[minIndex];
            arr[minIndex] = temp;
        }
    }
}

 

 

3. ์‚ฝ์ž… ์ •๋ ฌ

 

โš™๏ธ ๋กœ์ง

  1. ๋ฆฌ์ŠคํŠธ์˜ ์ฒซ ๋ฒˆ์งธ ์š”์†Œ๋Š” ์ด๋ฏธ ์ •๋ ฌ๋œ ๊ฒƒ์œผ๋กœ ๊ฐ„์ฃผํ•˜๊ณ  ๋‘ ๋ฒˆ์งธ ์š”์†Œ๋ถ€ํ„ฐ ์ •๋ ฌ์„ ์‹œ์ž‘ํ•œ๋‹ค.
  2. ๋‘ ๋ฒˆ์งธ ์š”์†Œ๋ฅผ ์ •๋ ฌ๋œ ๋ถ€๋ถ„์— ์‚ฝ์ž…ํ•  ์œ„์น˜๋ฅผ ์ฐพ์•„ ๋ฐฐ์น˜ํ•œ๋‹ค
  3. ์œ„ ๊ณผ์ •์„ ๋ฐ˜๋ณตํ•˜์—ฌ ์ •๋ ฌ๋œ ๋ถ€๋ถ„์„ ํ™•์žฅํ•œ๋‹ค. 
  • ์‹œ๊ฐ„ ๋ณต์žก๋„  : O(n^2)
  • ์ž‘์€ ๋ฐ์ดํ„ฐ์…‹, ๋Œ€๋ถ€๋ถ„ ์ •๋ ฌ๋œ ๋ฆฌ์ŠคํŠธ์— ์ ํ•ฉํ•˜๋‹ค. 


๐Ÿ“„ ์œ ํ˜• ์ดํ•ด ์ฝ”๋“œ

public class InsertionSort {
    public static void insertionSort(int[] arr) {
        int n = arr.length;
        for (int i = 1; i < n; i++) {
            int key = arr[i];
            int j = i - 1;
            while (j >= 0 && arr[j] > key) {
                arr[j + 1] = arr[j];
                j = j - 1;
            }
            arr[j + 1] = key;
        }
    }
}

 

 

4. ๋ณ‘ํ•ฉ ์ •๋ ฌ 

 

โš™๏ธ ๋กœ์ง

  1. ๋ฆฌ์ŠคํŠธ๋ฅผ ๋ฐ˜์œผ๋กœ ๋‚˜๋ˆ„์–ด ๋‘ ๊ฐœ์˜ ํ•˜์œ„ ๋ฆฌ์ŠคํŠธ๋กœ ๋ถ„ํ• 
  2. ๊ฐ ํ•˜์œ„ ๋ฆฌ์ŠคํŠธ๋ฅผ ์žฌ๊ท€์ ์œผ๋กœ ๋‹ค์‹œ ๋ถ„ํ• ํ•œ ๋’ค, ์ •๋ ฌํ•˜์—ฌ ๋ณ‘ํ•ฉ
  3. ๋ณ‘ํ•ฉ ๊ณผ์ •์—์„œ ๋‘ ๋ฆฌ์ŠคํŠธ์˜ ์ฒซ ์š”์†Œ๋ฅผ ๋น„๊ตํ•ด๊ฐ€๋ฉฐ ์ž‘์€ ๊ฐ’๋ถ€ํ„ฐ ์ฐจ๋ก€๋Œ€๋กœ ๋ณ‘ํ•ฉํ•œ๋‹ค.
  • ๋ถ„ํ• ์ •๋ณต ๊ธฐ๋ฒ•์„ ์‚ฌ์šฉํ•˜์—ฌ ๋ฆฌ์ŠคํŠธ ๋ถ„ํ• 
  • ์‹œ๊ฐ„ ๋ณต์žก๋„ : O(n log n)
  • ์•ˆ์ • ์ •๋ ฌ๋กœ, ๋ฐ์ดํ„ฐ์˜ ํฌ๊ธฐ์— ์ƒ๊ด€์—†์ด ์ผ์ •ํ•œ ์„ฑ๋Šฅ์„ ๋ณด์ธ๋‹ค.


๐Ÿ“„ ์œ ํ˜• ์ดํ•ด ์ฝ”๋“œ

public class MergeSort {
	// ๋ฐฐ์—ด์„ ๋ถ„ํ• ํ•˜๊ณ  ๋ณ‘ํ•ฉํ•˜๋Š” ๋ฉ”์„œ๋“œ
    // left : ์™ผ์ชฝ ๊ฒฝ๊ณ„, mid : ๋ฐฐ์—ด์˜ ์ค‘๊ฐ„์ , right : ์˜ค๋ฅธ์ชฝ ๊ฒฝ๊ณ„
    public static void mergeSort(int[] arr, int left, int right) {
        if (left < right) {
            int mid = (left + right) / 2;

            // ๋‘ ๊ฐœ์˜ ํ•˜์œ„ ๋ฆฌ์ŠคํŠธ์— ๋Œ€ํ•ด ์žฌ๊ท€์ ์œผ๋กœ mergeSort๋ฅผ ํ˜ธ์ถœํ•˜์—ฌ ์ •๋ ฌ
            mergeSort(arr, left, mid);
            mergeSort(arr, mid + 1, right);

            // ์ •๋ ฌ ํ›„, merge๋ฉ”์„œ๋“œ๋ฅผ ์ด์šฉํ•˜์—ฌ ๋‘ ๋ถ€๋ถ„ ๋ณ‘ํ•ฉ
            merge(arr, left, mid, right);
        }
    }

	// ๋‘ ๊ฐœ์˜ ์ •๋ ฌ๋œ ํ•˜์œ„ ๋ฐฐ์—ด์„ ํ•˜๋‚˜์˜ ์ •๋ ฌ๋œ ๋ฐฐ์—ด๋กœ ๋ณ‘ํ•ฉํ•˜๋Š” ์ž‘์—…
    public static void merge(int[] arr, int left, int mid, int right) {
        int n1 = mid - left + 1;
        int n2 = right - mid;
		
        // ๋‘ ๊ฐœ์˜ ๋ฐฐ์—ด์„ ๋งŒ๋“ค์–ด ์™ผ์ชฝ๊ณผ ์˜ค๋ฅธ์ชฝ ๋ถ€๋ถ„ ๋ฐฐ์—ด ์ €์žฅ
        int[] L = new int[n1];
        int[] R = new int[n2];
		
        for (int i = 0; i < n1; i++)
            L[i] = arr[left + i];
        for (int j = 0; j < n2; j++)
            R[j] = arr[mid + 1 + j];
		
        int i = 0, j = 0;
        int k = left;
        // L[i]์™€ R[i]๋ฅผ ๋น„๊ตํ•˜์—ฌ ๋” ์ž‘์€ ๊ฐ’์„ arr[k]์— ์ €์žฅ
        while (i < n1 && j < n2) {
            if (L[i] <= R[j]) {
                arr[k] = L[i];
                i++;
            } else {
                arr[k] = R[j];
                j++;
            }
            k++;
        }
		
        // ์–ด๋Š ํ•œ ์ชฝ ๋ฐฐ์—ด์ด ๋ชจ๋‘ ์ฒ˜๋ฆฌ๋˜๋ฉด, ๋‚˜๋จธ์ง€ ๋ฐฐ์—ด์— ๋‚จ์•„์žˆ๋Š” ๊ฐ’๋“ค์„ ๊ทธ๋Œ€๋กœ arr์— ๋ณต์‚ฌํ•œ๋‹ค.
        while (i < n1) {
            arr[k] = L[i];
            i++;
            k++;
        }

        while (j < n2) {
            arr[k] = R[j];
            j++;
            k++;
        }
    }
}

 

 

5. ํ€ต ์ •๋ ฌ

 

โš™๏ธ ๋กœ์ง

  1. ๋ฆฌ์ŠคํŠธ์—์„œ ํ•˜๋‚˜์˜ ํ”ผ๋ฒ—(pivot)์„ ์„ ํƒ
  2. ํ”ผ๋ฒ—๋ณด๋‹ค ์ž‘์€ ๊ฐ’๋“ค์„ ํ”ผ๋ฒ—์˜ ์™ผ์ชฝ, ํฐ ์š”์†Œ๋“ค์„ ์˜ค๋ฅธ์ชฝ์œผ๋กœ ์œ„์น˜ ์‹œํ‚จ๋‹ค
  3. ์œ„ ๊ณผ์ •์„ ์žฌ๊ท€์ ์œผ๋กœ ๋ฐ˜๋ณต 
  • ๋ถ„ํ•  ์ •๋ณต ๊ธฐ๋ฒ• ์‚ฌ์šฉ
  • ์‹œ๊ฐ„ ๋ณต์žก๋„ : O(n^2)
  • ์ตœ์•…์˜ ๊ฒฝ์šฐ ์‹œ๊ฐ„ ๋ณต์žก๋„๋Š” ๋†’์ง€๋งŒ, ์ด๋ฅผ ์œ„ํ•œ ์—ฌ๋Ÿฌ ์ตœ์ ํ™” ๊ธฐ๋ฒ•์ด ์กด์žฌํ•˜์—ฌ ์‹œ๊ฐ„์„ ๋‹จ์ถ•์‹œํ‚ฌ ์ˆ˜ ์žˆ๋‹ค. 


๐Ÿ“„ ์œ ํ˜• ์ดํ•ด ์ฝ”๋“œ

public class QuickSort {
	// ๋ฐฐ์—ด์˜ ๋ถ€๋ถ„๋“ค์„ ์žฌ๊ท€์ ์œผ๋กœ ์ •๋ ฌํ•˜๋Š” ๋ฉ”์„œ๋“œ
    // low : ๋ฐฐ์—ด์˜ ์‹œ์ž‘ ์ธ๋ฑ์Šค(์™ผ์ชฝ ๊ฒฝ๊ณ„), high : ๋ฐฐ์—ด์˜ ๋ ์ธ๋ฑ์Šค(์˜ค๋ฅธ์ชฝ ๊ฒฝ๊ณ„)
    public static void quickSort(int[] arr, int low, int high) {
    	// low์™€ high๊ฐ€ ๋งŒ๋‚˜์ง€ ์•Š์€ ๋™์•ˆ ๋ฐฐ์—ด์„ ํ”ผ๋ฒ— ๊ธฐ์ค€์œผ๋กœ ๋ถ„ํ• 
        if (low < high) {
            int pi = partition(arr, low, high);

            // ํ”ผ๋ฒ—์„ ๊ธฐ์ค€์œผ๋กœ ์™ผ์ชฝ ๋ถ€๋ถ„ ๋ฐฐ์—ด๊ณผ ์˜ค๋ฅธ์ชฝ ๋ถ€๋ถ„ ๋ฐฐ์—ด์— ๋Œ€ํ•ด ๊ฐ๊ฐ ์žฌ๊ท€์ ์œผ๋กœ quickSort๋ฅผ ํ˜ธ์ถœํ•˜์—ฌ ์ •๋ ฌ
            quickSort(arr, low, pi - 1);
            quickSort(arr, pi + 1, high);
        }
    }
    
	// ํ”ผ๋ฒ—์„ ๊ธฐ์ค€์œผ๋กœ ๋ฐฐ์—ด์„ ๋‘ ๋ถ€๋ถ„์œผ๋กœ ๋‚˜๋ˆ„๊ณ , ๊ทธ ์ธ๋ฑ์Šค๋ฅผ ๋ฐ˜ํ™˜ํ•˜๋Š” ๋ฉ”์„œ๋“œ
    public static int partition(int[] arr, int low, int high) {
        int pivot = arr[high];
        int i = (low - 1);
        // arr[j]์™€ ํ”ผ๋ฒ—์„ ๋น„๊ตํ•˜์—ฌ arr[j]๊ฐ€ ํ”ผ๋ฒ—๋ณด๋‹ค ์ž‘์œผ๋ฉด, i๋ฅผ ์ฆ๊ฐ€์‹œํ‚ค๊ณ  arr[i]์™€ arr[j]๋ฅผ ๊ตํ™˜ํ•œ๋‹ค.
        for (int j = low; j < high; j++) {
            if (arr[j] < pivot) {
                i++;
                // Swap arr[i] and arr[j]
                int temp = arr[i];
                arr[i] = arr[j];
                arr[j] = temp;
            }
        }
        // arr[i + 1]์™€ ํ”ผ๋ฒ—(arr[high])์„ ๊ตํ™˜ํ•˜์—ฌ ํ”ผ๋ฒ—์„ ์˜ฌ๋ฐ”๋ฅธ ์œ„์น˜์— ๋†“๋Š”๋‹ค
        int temp = arr[i + 1];
        arr[i + 1] = arr[high];
        arr[high] = temp;

        return i + 1;
    }
}

 

 

๐Ÿ“์ •๋ ฌ ์•Œ๊ณ ๋ฆฌ์ฆ˜ ์„ ํƒ ๊ธฐ์ค€

: ๋ฌธ์ œ์˜ ํŠน์„ฑ์— ๋งž๋Š” ์ตœ์ ์˜ ๋ฐฉ๋ฒ•์„ ์„ ํƒํ•ด์•ผํ•œ๋‹ค.

  • ๋ฐ์ดํ„ฐ์˜ ํฌ๊ธฐ
  • ๋ฐ์ดํ„ฐ ๊ตฌ์กฐ ๋ฐ ์ƒํƒœ : ์ •๋ ฌ ์ •๋„ / ์ •๋ ฌ ๊ตฌ์กฐ ๋“ฑ
  • ๊ณต๊ฐ„ ํšจ์œจ์„ฑ : ์ถ”๊ฐ€ ๋ฉ”๋ชจ๋ฆฌ์˜ ํฌ๊ธฐ
  • ์•ˆ์ •์„ฑ : ์ค‘๋ณต๋œ ๊ฐ’์˜ ์ˆœ์„œ ์œ ์ง€๊ฐ€ ์ค‘์š”ํ•œ ๊ฒฝ์šฐ
  • ์†๋„