https://www.acmicpc.net/problem/20920
20920번: 영단어 암기는 괴로워
첫째 줄에는 영어 지문에 나오는 단어의 개수 $N$과 외울 단어의 길이 기준이 되는 $M$이 공백으로 구분되어 주어진다. ($1 \leq N \leq 100\,000$, $1 \leq M \leq 10$) 둘째 줄부터 $N+1$번째 줄까지 외울 단
www.acmicpc.net
Code
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.HashMap;
import java.util.List;
import java.util.StringTokenizer;
import java.util.stream.Collectors;
public class Main {
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st = new StringTokenizer(br.readLine());
HashMap<String,Integer> map = new HashMap<>();
int n = Integer.parseInt(st.nextToken());
int m = Integer.parseInt(st.nextToken());
String[] arr = new String[n];
for(int i=0;i<n;i++) {
arr[i] = br.readLine();
}
for(int i=0;i<n;i++) {
if(arr[i].length() >= m) {
if(map.containsKey(arr[i])) {
map.put(arr[i], map.get(arr[i])+1);
}
else {
map.put(arr[i], 1);
}
}
}
List<String> words = map.keySet().stream().collect(Collectors.toList());
words.sort((o1,o2)->{
int c1 = map.get(o1);
int c2 = map.get(o2);
if(c1==c2) {
if(o1.length() == o2.length()) {
return o1.compareTo(o2);
}
return o2.length()-o1.length();
}
return c2-c1;
});
StringBuilder sb = new StringBuilder();
for(int i=0;i<words.size();i++) {
sb.append(words.get(i)).append("\n");
}
System.out.println(sb);
br.close();
}
}
map을 사용해서 문자열의 빈도를 저장하는 것까진 했는데 그 뒤로 어떻게 해야 할지 생각이 잘 안 났다.
인터넷을 찾아보고 풀었는데 모르는 부분이 많았다.
List <String> words = map.keySet(). stream(). collect(Collectors.toList());
먼저, 이 부분은 map이라는 맵(Map) 객체에서 키(Key)들을 추출하여 스트림(Stream)으로 변환한 뒤, 해당 스트림을 Collectors.toList()를 사용하여 리스트(List) 객체로 수집(collect)하는 역할을 한다.
어려운 말이라 이해가 잘 안 되는데 List에 map의 key값들을 추출해서 저장해 준다고 생각하고 있다.
words.sort((o1, o2)->{
int c1 = map.get(o1);
int c2 = map.get(o2);
if(c1==c2) {
if(o1.length() == o2.length()) {
return o1.compareTo(o2);
}
return o2.length()-o1.length();
}
return c2-c1;
});
다음은 이 부분인데, 람다식이 쓰였다.람다식을 사용할 때 o1,o2 이 부분이 선언 없이 사용된 것에 의문이 있었는데 람다식에서는 콘텍스트에서 암묵적으로 타입 추론을 통해 자동으로 추론되는 매개변수로 사용된다고 한다.
c1과 c2는 key값의 빈도수를 의미하고 값이 같을 때 길이를 비교하게 된다.반환값에서 compareTo가 사용되었는데 두 객체를 비교해서 정수값을 반환하게 한다.0이라면 두 값이 같다는 의미이고 음수라면 앞의 값이 작으니 정렬순서상 앞에 위치한다는 의미이다.반대로 양수라면 두 번째 값이 작으니 정렬순서상 뒤에 위치한다는 의미이다.
그렇게 저장된 words를 StringBuilder에 넣어 출력한다.
'백준' 카테고리의 다른 글
백준[15829]번 : Hashing ( JAVA ) (0) | 2023.05.10 |
---|---|
백준[1920]번: 수 찾기 ( JAVA ) (2) | 2023.04.15 |
백준[26069]번 : 붙임성 좋은 총총이 ( JAVA ) (0) | 2023.04.08 |
백준[25192]번 : 인사성 밝은 곰곰이 ( JAVA ) (0) | 2023.04.08 |
백준[24723]번 : 녹색거탑 ( JAVA ) (2) | 2023.04.08 |