알고리즘/프로그래머스

[프로그래머스] 체육복 for JAVA

정석이 2021. 10. 21. 21:07

 

 

 

 


 

 

그리디 알고리즘에 분류되어있는 level1짜리 문제이다.

 

 

 

내가 풀려던 방법은 arraylist에 1~n까지의 수를 다 넣고 lost인 사람의 숫자를 없애고 reserve -1 과 +1을 비교해서 넣는 방법을 사용하려고 했는데

 

 

모든 테스트케이스를 통과하지 못했다.. 50점이었나...? 지금 보니 왜 저렇게 짰는지...

 

 

 

 

그래서 남의 코드를 봤다!!

 

 

내걸로 만들려고 리뷰할거다.

 

 

 

 

 

풀이1

 

 

1. 먼저 여벌 체육복을 가져온 학생이 잃어버렸으면 +-0이므로 걔네 먼저 확인해줘야한다.

 

2중 for문으로 lost 배열과 reserver 배열에 같은 값이 있는지 확인하고 같은 값이 있다면 answer에 +1 해주고(수업참여 가능) 두 배열 값을 -1로 초기화한다.

 

 

2. 도난당한 학생에게 체육복 빌려주기

 

여분이 있는 학생은 자기 앞뒤 학생에게만 빌려줄 수 있으니까 reserve[i] -1 || reserve[i] +1 에게 빌려줄 수 있다. 또는 lost[i] -1 || lost[i] +1이 reserve[i]에게 빌릴 수 있다.

 

2중 for문으로 lost와 reserve 배열을 훑으면서 후자의 방법으로 lost가 reserve에게 빌릴 수 있는지 확인한다. 빌릴 수 있다면 answer++ 해주고 빌려준 학생은 여분이 없으므로 reserve[] 배열 값을 -1로 초기화한다.

 

 

 

 

 

 

남의코드 확인

 

import java.util.Arrays;
class Solution {
    public int solution(int n, int[] lost, int[] reserve) {
        int answer = n - lost.length;
        
        Arrays.sort(lost);
        Arrays.sort(reserve);
        // 두 배열 모두 정렬하고 시작하자
        
        // 여벌 체육복을 가져온 학생이 도난당한 경우
        for(int i=0; i<lost.length; i++){
            for(int j=0; j<reserve.length; j++){
                if(lost[i] == reserve[j]){
                    answer++;
                    lost[i] = -1;
                    reserve[j] = -1; //초기화
                    break; 
                }
            }
        }
        // 도난당한 학생에게 체육복 빌려주는 경우
        for(int i=0; i<lost.length; i++){
            for(int j=0; j<reserve.length; j++){
                if((lost[i]-1 == reserve[j]) || (lost[i]+1 == reserve[j])){  // 누구에게 빌릴 수 있으면
                    answer++;
                    reserve[j] = -1; //초기화
                    break; 
                }
            }
        }
        return answer;
    }
}

 

 

 

 

 

 

 

 

 

프로그래머스에 있는 풀이2

 

 

 

1. people 배열을 n만큼 선언해준다.

 

2. answer = n으로 해준다.

 

3. people배열을 lost면  -1, reserve면 +1로 바꿔준다.

 

4. if(lost의 번호이면)

       if(맨 앞번호가 아니고 앞자리 사람(i-1)이 여분이 있으면(=1이면))

             people 배열 lost번호인 사람 = 0 으로 초기화

             빌려준 앞번호 사람 (i-1) 도 0으로 초기화

   else if ( 맨 마지막 번호가 아니고 뒷자리 사람이 여분이 있으면)

             (위와같음)

 

   else = 빌릴사람이 없다면

            answer -1로 한명 체육에 참여 못함

 

 

4-1. 맨 앞번호는 앞번호 사람이 없으므로 뒷사람에게만 빌릴 수 있고, 맨 뒷번호도 앞번호 사람에게만 빌릴 수 있다.

 

 

 

 

 

 

그분 코드

 

class Solution {
    public int solution(int n, int[] lost, int[] reserve) {
        int[] people = new int[n];
        int answer = n;

        for (int l : lost) 
            people[l-1]--;
        for (int r : reserve) 
            people[r-1]++;

        for (int i = 0; i < people.length; i++) { // 맨 앞번호 x + 앞사람에게 빌리기
            if(people[i] == -1) {
                if(i-1>=0 && people[i-1] == 1) {
                    people[i]++;   // 빌렸으니 -1 -> 0
                    people[i-1]--;  // 빌려줬으니 1 -> 0
                }else if(i+1< people.length && people[i+1] == 1) { // 맨 뒷번호x + 뒷사람에게 빌리기
                    people[i]++;
                    people[i+1]--;
                }else 
                    answer--;   // 체육 참여 못함
            }
        }
        return answer;
    }
}

 

 

 

 

 

 

 


 

 

프로그래머스... 레벨 1부터 어렵구나....

 

나는 너무 arraylist를 사용해서 효율을 올려야한다는 강박이 있는듯ㅋㅋㅋㅋ 오히려 효율 떨어져!

 

 

 

 

 

+

 

시험기간이라 할거 너무 많아서 너무 게을렀다...흑흑

 

 

대기업 원서 그냥 넣어봤는데 서합해서 코테때문에 스트레스 너무 받았다...ㅠㅠ 너무 코찐;;

 

프로그래머스는.. ide 제공이 안돼서 자동완성으로 하던 나에게 너무 큰 시련이닷ㅋ!!

 

 

얼른 영어점수 따고 코테 공부 열심히해야지! 화이팅!