여니의 취준 준비/코딩테스트 (Java)

[*1828*] 냉장고 in Java (feat. 정올, Comparator, Comparable 차이 및 설명)

여니's 2022. 8. 16. 17:56

http://www.jungol.co.kr/bbs/board.php?bo_table=pbank&code=1828&sca=99 

 

JUNGOL

 

www.jungol.co.kr

https://m.blog.naver.com/PostView.naver?isHttpsRedirect=true&blogId=hwadla&logNo=220885232086 

 

[Java][Jungol] 문제풀기 - 기초다지기 출력 자가진단 1

[Java][Jungol] 문제풀기 - 기초다지기 출력 자가진단 1 자바 언어로 정올문제 풀기 시작합니다. 재미있...

blog.naver.com

-> 정올 코드 제출시 지켜야하는 클래스명 (Main)

해당 문제와 비슷한 문제

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

 

1931번: 회의실 배정

(1,4), (5,7), (8,11), (12,14) 를 이용할 수 있다.

www.acmicpc.net


문제 접근 방식 

-> 적정한 온도에서 화학물질을 보관할 때

가능하면 적은 수의 냉장고를 사용하도록 하는 알고리즘을 설계해야 하는 문제

 

최고 기온 기준으로 오름차순 정렬,

최고 기온이 같다면 최저 기온으로 오름차순 정렬

-> 최고기온이 다음 화학물질의 최저 온도보다 낮으면 냉장고 +1

-> 최고 기온이 최저 온도랑 같다면? -> 최저 온도를 비교한다 -> 최저 온도가 더 낮은 경우를 냉장고로 선택 +1

 

 

 


 시행 착오

 

1. 문제를 잘못 이해함

화학 물질을 안전하게 보관할 수 있는 온도의 범위가

예를 들어 -15(최저온도)~5(최고온도) 범위내에만 속하면 되는 것이다.

그런데 나는 전체 범위 중 일부에 속하는 온도가 아닌

전체 범위를 한 덩어리로 생각했다.

 

그래서 (-15,5)가 (-10,36) 냉장고에 포함될 수 없다고 잘못 생각했다.

 


2. 정렬 기준 변경하는 방법

(1) 람다식 사용

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
package day_0816;
 
import java.util.Arrays;
import java.util.Scanner;
 
public class ComparatorTest {
    
    
    public static void main(String[] args) {
        Scanner sc=new Scanner(System.in);
        int[][] persons= new int[3][2]; 
        for (int i = 0; i < 3; i++) {
            int age=sc.nextInt();
            int budget=sc.nextInt();
            persons[i][0]=age;
            persons[i][1]=budget;
        }
        Arrays.sort(persons,(o1,o2) -> o2[0]-o1[0]); // 나이순 내림차순
        for (int i = 0; i < persons.length; i++) {
            System.out.println(persons[i][0]+ " , " + persons[i][1]);
        }    
        System.out.println("__________________________");
        Arrays.sort(persons,(o1,o2) -> o1[0]-o2[0]); // 나이순 오름차순
        for (int i = 0; i < persons.length; i++) {
            System.out.println(persons[i][0]+ " , " + persons[i][1]);
        }    
    }
}
 
/*
입력값 예
15 30
15 14
22 19
*/
 
cs

 

-> 최고 보관 온도를 기준으로 오름차순 ,

최고 보관 온도가 같다면 최저 보관 온도 기준으로 오름차순으로 

정렬하려면 compareTo 메서드를 오버라이딩 해야한다.

이 부분이 아직 낯설다..

 


(2) Comparable vs Comparator

(1) Comparable

: Class에 정렬 기준을 정해주는 것

즉 객체의 정렬 기준을 만들어주기 위해 사용한다.

String 타입 같은 경우에는 Arrays.sort를 사용하면

사전순으로 정렬할 수 있다.

 

하지만 객체는 정렬 기준이 없다.

따라서 객체의 클래스에서 Comparable 인터베이스를 구현하여

객체 기준을 만들어주는 방식으로 사용이 된다.

 

 

사용방법)

클래스에 Comparable를 implements 하고,

compareTo를 오버라이딩 하여 재정의한다.

 

양수 or 1을 리턴 : 두 객체의 자리가 바뀐다.

음수 or 0을 리턴 : 두 객체의 위치가 바뀌지 않는다.

 

 

compareTo() 메서드)

: 두 개의 값을 비교해서 int 값을 반환해주는 함수

정렬 조건을 변경할 땐 객체의 compareTo() 함수를 오버라이딩하여

재정의를 해줘야한다.

 

 

1
2
3
4
5
6
7
8
9
10
11
12
13
 static class Refrigerator implements Comparable<Refrigerator>{
    int lower,higher;
    public Refrigerator(int lower, int higher){
        this.lower=lower;
        this.higher=higher;
    }
    @Override
    public int compareTo(Refrigerator o){
        return this.higher!=o.higher? this.higher-o.higher : this.lower-o.lower;
    }
}
 
 
cs

 

(2) Comparator

: Comparable과 마찬가지로 객체의 정렬기준을 정할때 사용된다.

이미 정해진 정렬 기준과 다르게 정렬하고 싶을 때 사용한다.

하지만 Comparator의 구현체는 클래스 자체가 정렬 기준으로 사용된다.

즉, 외부 정렬기준을 정의한다는 의미이다.

 

사용 방법)

클래스에 Comparator를 implements 하고,

compare를 오버라이딩하여 재정의한다.

 

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
package day_0816;
 
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;
import java.util.Scanner;
 
public class ComparatorTest {
    
    static class Person implements Comparable<Person>{
        int age, budget; // 나이, 예산
        
        public Person(int age, int budget) {
            super();
            this.age = age;
            this.budget = budget;
        }
 
        @Override
        public int compareTo(Person o) {
            // this.age==o1(앞) o.age==o2(뒤) 
            // age를 내림차순으로, 만약 age가 같다면 budget을 내림차
            // o.age-this.age ->
            // 만약 o.age가 11, this.age가 9라면? 9 11로 위치해있는 상태
            // o.age-this.age->11-9->2로 양수가 나왔다.
            // 양수면 값을 뒤바꿔줘야 한다. 바꾸면  9 11 -> 11 9가 되고
            // 내림차순으로 변경이 된다. 
            return this.age!=o.age ? o.age-this.age : o.budget-this.budget;
        }        
    }
     
    static class AgeSort implements Comparator<Person>{
        @Override
        public int compare(Person o1, Person o2) {
            // 
            return o1.compareTo(o2)*-1// 나이 기준 오름차순 정렬
        }
    }
    
    static class budgetSort implements Comparator<Person>{
        @Override
        public int compare(Person o1, Person o2) {
            return o1.compareTo(o2)*-1// 예산 기준 오름차순 정렬
        }
    }
    
    public static void main(String[] args) {
        Scanner sc=new Scanner(System.in);
        Person[] persons= new Person[3]; 
        for (int i = 0; i < 3; i++) {
            int age=sc.nextInt();
            int budget=sc.nextInt();
            persons[i]=new Person(age,budget);
        }
        List<Person> result = getPerson(persons);
        for (int i = 0; i < 3; i++) {
            System.out.println(result.get(i).age+" " + result.get(i).budget);
        }
        List<Person> list = new ArrayList<>();
        for (int i = 0; i < persons.length; i++) {
            list.add(persons[i]);
        }
        
        System.out.println("나이 기준 오름차순 정렬");
        Collections.sort(result, new AgeSort());
        for (int i = 0; i < persons.length; i++) {
            System.out.println(result.get(i).age+" " + result.get(i).budget);            
        }
        
        System.out.println("예산 기준 오름차순 정렬");
        Collections.sort(result, new budgetSort());
        for (int i = 0; i < persons.length; i++) {
            System.out.println(result.get(i).age+" " + result.get(i).budget);            
        }
    }
 
    private static List<Person> getPerson(Person[] persons) {
        List<Person> result = new ArrayList<Person>();
        Arrays.sort(persons);
        result.add(persons[0]);
        result.add(persons[1]);
        result.add(persons[2]);
        return result;
    }
 
}
 
/*
입력값 예
15 30
15 14
22 19
*/
 
cs

 

 

 

 

 


문제 소스 코드

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
package day_0816;
 
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.StringTokenizer;
 
public class j1828 {
    static class Refrigerator implements Comparable<Refrigerator>{
        int lower,higher;
        public Refrigerator(int lower,int higher) {
            this.lower=lower;
            this.higher=higher;
        }
        @Override
        public int compareTo(Refrigerator o) {
            // 최고 보관 온도 기준 오름차순, 최고 보관 온도 같다면 최저 보관 온도 기준 오름차순
            return this.higher!=o.higher? this.higher-o.higher : this.lower-o.lower;
        }
        
    }
 
    
    static int N;
    
    // http://www.jungol.co.kr/bbs/board.php?bo_table=pbank&wr_id=1101&sca=99&sfl=wr_subject&stx=%EB%83%89%EC%9E%A5%EA%B3%A0
    public static void main(String[] args) throws IOException {
        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        N=Integer.parseInt(br.readLine()); // 화학물질의 수
        Refrigerator[] refrigerators = new Refrigerator[N];
        for (int i = 0; i < N; i++) {
            StringTokenizer st = new StringTokenizer(br.readLine());
            // 온도 xi이상, yi이하의 온도에서 보관되어야만 안전
            // 가능하면 적은 수의 냉장고를 사용
            int lower=Integer.parseInt(st.nextToken()); // 최저 보관 온도
            int higher=Integer.parseInt(st.nextToken()); // 최고 보관 온도
            refrigerators[i]=new Refrigerator(lower, higher);
        }
        List<Refrigerator> result = getRefrigerator(refrigerators);
        System.out.println(result.size());
    }
 
    private static List<Refrigerator> getRefrigerator(Refrigerator[] refrigerators) {
        List<Refrigerator> result=new ArrayList<Refrigerator>();
        Arrays.sort(refrigerators);
        result.add(refrigerators[0]);
        for (int i = 1,size=refrigerators.length; i < size; i++) {
            if(result.get(result.size()-1).higher<=refrigerators[i].lower) {
                result.add(refrigerators[i]);
            }
        }
        return result;
    }
 
}
 
cs

 

 


참고 자료

https://velog.io/@ovan/Comparable-Comparator

 

Comparable, Comparator 차이

Comparable은 Java.lang package에 있는 인터페이스이며 정렬을 위해 사용되는데, 보통 기본형(Primitive Type)을 정렬하는데 사용하지는 않습니다.Comparable을 사용하는것은 객체(Object)의 정렬기준을 만들어

velog.io

 

'여니의 취준 준비 > 코딩테스트 (Java)' 카테고리의 다른 글

[*1992*] 쿼드트리 in Java  (0) 2022.08.18
[*5644*] 무선 충전 in Java (Feat. SWEA)  (0) 2022.08.17
[20207] 달력 in Java  (0) 2022.08.14
[17471] 게리맨더링 in Java  (0) 2022.08.14
[17281]⚾ in Java  (0) 2022.08.12