https://st-lab.tistory.com/108?category=857114
[백준] 2108번 : 통계학 - JAVA [자바]
www.acmicpc.net/problem/2108 2108번: 통계학 첫째 줄에 수의 개수 N(1 ≤ N ≤ 500,000)이 주어진다. 그 다음 N개의 줄에는 정수들이 주어진다. 입력되는 정수의 절댓값은 4,000을 넘지 않는다. www.acmicpc.net..
st-lab.tistory.com
*해당 포스팅은 상단에 링크된 포스팅을 바탕으로 개인 공부 목적을 위해 작성되었으므로 자세한 내용은 위 링크를 확인해 주시기 바랍니다.
여기서도 그냥 Arrays.sort()를 썼었는데 역시나 선생님은 시간 복잡도를 고려해서 카운팅 정렬을 쓰셨다. O(n)과 O(nlogn)은 천지차이라는 선생님의 말씀을 새겨들어야지. 나는 이 문제에서 최빈값이 되게 어려웠는데 이해가 잘 안 가서 손으로 다시 코드도 쓰고 값이 어떻게 변하는지 표로 그려보니까 조금씩 이해가 갔다. 그리고 max값이랑 min값 구하는 게 다시 한번 정리가 되서 좋았다.
아예 입력값을 받으면서부터 합계도 더하고 정렬도 하고 심지어 최댓값 최솟값까지 정리를 해놨다. max를 Integer.MAX_VALUE로 하고 min을 Integer.MIN_VALUE로 해서 입력값이 max보다 크면 max값을 갱신하고 입력값이 min보다 작으면 min값을 갱신하는 게 신박했다. 이런 건 학교에서 배우는 건가..? 나는 아직 배울 게 참 많구나. 중앙값은 배열의 크기에서 1을 더한 값에 2를 나눈 게 배열의 해당 인덱스 값보다 클 때까지 반복을 하면서 구하는데 정말 간결해서 좋았다.
예를 들어 1, 3, 8, -2, 2가 입력되면 배열 중에 해당하는 숫자의 인덱스 값이 다 1로 오른다.
count는 0에서 시작이 되고 (N + 1) / 2 = 6 가 될 때까지 반복한다.
count | median |
1 | -2 |
2 | 1 |
3 | 2 |
이렇게 중앙값 2를 구할 수 있다.
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
public class Main {
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
int N = Integer.parseInt(br.readLine());
int[] arr = new int[8001];
int sum = 0;
int max = Integer.MIN_VALUE;
int min = Integer.MAX_VALUE;
int median = 10000;
int mode = 10000;
for(int i = 0; i < N; i++) {
int value = Integer.parseInt(br.readLine());
sum += value;
arr[value + 4000]++;
if(max < value) {
max = value;
}
if(min > value) {
min = value;
}
}
int count = 0; // 중앙값 빈도 누적 수
int mode_max = 0; // 최빈값의 최댓값
// 이전의 동일한 최빈값이 1번만 등장했을 경우 true, 아니면 False
boolean flag = false;
for(int i = min + 4000; i <= max + 4000; i++) {
if(arr[i] > 0) {
if (count < (N+1) / 2) {
count += arr[i];
median = i - 4000;
}
}
if (mode_max < arr[i]) {
mode_max = arr[i];
mode = i - 4000;
flag = true;
}
else if(mode_max == arr[i] && flag) {
mode = i - 4000;
flag = false;
}
}
System.out.println((int)Math.round((double)sum / N)); // 산술평균
System.out.println(median);
System.out.println(mode);
System.out.println(max - min);
}
}
산술평균 출력의 경우에는 sum과 N 둘중에 하나는 double형으로 캐스팅 해줘야 소수점을 버리지 않을 수 있고 거기서 반올림을 해준 후에 int형으로 캐스팅해야 한다고 한다!
'Computer Science > Algorithm' 카테고리의 다른 글
[백준] 10989 - 수 정렬하기 3 (Java) (0) | 2022.09.21 |
---|---|
[백준] 2751 - 수 정렬하기 2 (Java) (0) | 2022.09.21 |
[백준] 2750 - 수 정렬하기 (Java) (0) | 2022.09.21 |
[백준] 9020 - 골드바흐의 추측 (Java) (0) | 2022.09.20 |
[백준] 2581 - 소수 (Java) (1) | 2022.09.19 |