백준_11582번_치킨 TOP N

임정민·2023년 2월 15일
3

알고리즘 문제풀이

목록 보기
34/173
post-thumbnail

코딩테스트 연습 스터디 진행중 입니다. ✍✍✍
Notion : https://www.notion.so/1c911ca6572e4513bd8ed091aa508d67

문제

https://www.acmicpc.net/problem/11582

[나의 풀이]

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.util.ArrayList;
import java.util.Collections;
import java.util.StringTokenizer;

public class Main {

    public static void main(String[] args) throws IOException {

        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(System.out));
        StringTokenizer st;

        int n = Integer.parseInt(br.readLine());
        ArrayList<Integer> list1 = new ArrayList<>();
        st = new StringTokenizer(br.readLine());

        for (int i = 0; i < n; i++) {
            list1.add(Integer.parseInt(st.nextToken()));
        }

        int k = Integer.parseInt(br.readLine());

        // 간격
        int div = n / k;

        ArrayList<Integer> ans = new ArrayList<>();

        for (int i = 0; i < n; i += div) {

            // subList : 파이썬의 인덱싱
            ArrayList<Integer> list2 = new ArrayList<>(list1.subList(i, i + div));
            Collections.sort(list2);

            // addAll : ArrayList에 자료구조 모든 데이터를 다 넣음
            ans.addAll(list2);
        }

        for (int i = 0; i < ans.size(); i++) {
            bw.write(ans.get(i) + " ");
        }

        bw.flush();

    }

}

[팀원의 풀이]

# coding = utf-8

import sys
input = sys.stdin.readline

n = int(input())
num_list = list(map(int,input().split()))
k = int(input())

def merge(ls1, ls2) :
    tmp = list()
    l, r = 0, 0
    while len(ls1) > l and len(ls2) > r :
        if ls1[l] > ls2[r] :
            tmp.append(ls2[r])
            r += 1
        else :
            tmp.append(ls1[l])
            l += 1
    tmp += ls1[l:]
    tmp += ls2[r:]
    return tmp

idx = n//2
print(idx)
while True :
    if idx < k :
        break
    leng = n//idx
    print(leng)
    for i in range(0,n-leng+1,leng) :
        left_ls = num_list[i:i+(leng//2)]
        right_ls = num_list[i+(leng//2):i+leng]
        print(left_ls, right_ls)
        num_list[i:i + leng] = merge(left_ls, right_ls)
        print(merge(left_ls, right_ls))
    idx //= 2
print(*num_list)

정렬/분할정복 알고리즘 문제입니다. 위 문제의 본 의도는 병합 정렬입니다. Merge 정렬의 특정 단계를 출력하는 문제인데 알고리즘 교재에서 공부한 내용이나 구글링해서 찾아본 소스들을 보면 문제에서 요구한 방법과 상이했습니다.

기본적으로 병합 정렬이라고 하면 맨처음에는 [a,b][c,d][e,f][g,h]..2개씩 쌍지어 정렬, 그 다음으로 [a,b,c,d][e,f,g,h] 4개씩 쌍지어 정렬...8개...16개...씩 정렬하는 방식입니다. 🙊🙊🙊

하지만 구글링해본 내용에 의하면 대부분 아래와 같이 [a,b]정렬, [c,d]정렬 ,[a,b,c,d]정렬,[a,b,c,d,e,f,g,h]정렬 하며 확장되는 방식이였습니다.

참고: 'Do it 자료구조와 함께하는 알고리즘 Java' 도서

import java.util.Arrays;

public class page243_merge_sort2 {

    static int[] buff;

    static void merge_sort1(int[] a, int n) {

        // 작업용 배열 buff
        buff = new int[n];

        merge_sort2(a, 0, n - 1);

        buff = null;
    }

    static void merge_sort2(int[] a, int left, int right) {

        if (left < right) {

            int i;
            int center = (left + right) / 2;
            int p = 0;
            int j = 0;
            int k = left;

            merge_sort2(a, left, center);
            merge_sort2(a, center + 1, right);

            for (i = left; i <= center; i++) {
                buff[p++] = a[i];

            }

            System.out.println("buff:" + Arrays.toString(buff));

            while (i <= right && j < p) {
                a[k++] = (buff[j] <= a[i]) ? buff[j++] : a[i++];
            }

            while (j < p) {
                a[k++] = buff[j++];
            }
            System.out.println("a :" + Arrays.toString(a));

        }

    }

    public static void main(String[] args) {

        int[] a = new int[] { 6, 4, 3, 7, 1, 9, 8, 2 };

        merge_sort1(a, a.length);

    }

위처럼 병합 정렬이지만 문제에서 요구하는 방식과는 달라 병합 정렬의 특징 중 하나인 병합하면서 크기가 2배로 커지는 작업 ArrayList를 활용해 K명의 회원이 정렬하는 ArrayList만 계산하여 해결할 수 있었습니다.🐱🐱🐱

오늘 문제 모르는 내용을 구글링한 내용이 틀릴 수도 있구나라고 큰 깨달음을 얻은 문제였습니다... 심지어 네임드(?) 블로그였던것으로 기억합니다...💦💦💦

감사합니다!!!

profile
https://github.com/min731

1개의 댓글

comment-user-thumbnail
2023년 2월 28일

답글 달기