
내가 생각했을때 문제에서 원하는부분
The input will consist of two lines.
The first line will contain the size of the word and the second the word to process.
The word will only contain lowercase letters from a to z.
The size of the word will be at most 1000 characters.
No spaces or other symbols will appear.
Print a single line with the character that appears the most and the number of occurrences.
내가 이 문제를 보고 생각해본 부분
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));:
표준 입력(키보드)으로부터 데이터를 읽어오기 위한 BufferedReader 객체를 생성한다.
System.in이 표준 입력 스트림이고, InputStreamReader가 이를 BufferedReader가 처리할 수 있는 문자 스트림으로 바꿔주는 역할을 한다.
int wordLength = Integer.parseInt(br.readLine());:
첫 번째 줄을 읽어서 br.readLine()으로 문자열 형태로 가져온다.
이 문자열은 단어의 길이를 나타내는 숫자이므로, Integer.parseInt()를 사용해서 정수(int)로 변환하여 wordLength 변수에 저장한다.
문제 해결 로직에서는 이 변수가 필수적이지는 않지만, 입력 형식에 맞춰 읽어두는 것이 좋다.
String pirateWord = br.readLine();:
두 번째 줄을 읽어서 해적 단어(pirateWord)를 문자열 형태로 가져온다.
int[] charCounts = new int[26];:
알파벳 'a'부터 'z'까지 총 26개의 문자가 있다.
charCounts라는 정수형 배열을 만들어서 각 알파벳이 몇 번 등장했는지 그 횟수를 저장한다.
charCounts[0]은 'a'의 횟수를, charCounts[1]은 'b'의 횟수를... 이런 식으로 charCounts[25]는 'z'의 횟수를 저장하게 된다.
for (int i = 0; i < wordLength; i++) { ... }:
pirateWord의 각 문자를 하나씩 살펴보기 위한 for 반복문이다.
wordLength만큼 반복한다.
char ch = pirateWord.charAt(i);:
pirateWord에서 i번째 위치에 있는 문자를 ch 변수에 저장한다. (예: "arrrrrghh"의 i가 0일 때는 'a', i가 1일 때는 'r'이 되겠다.)
charCounts[ch - 'a']++;:
이것이 알파벳 문자를 배열의 인덱스로 변환하는 방법이다.
자바에서 문자(char)는 사실 내부적으로 숫자로 저장된다 (아스키 코드).
'a'는 특정 숫자 값을 가지고, 'b'는 'a'보다 1 큰 숫자 값을 가진다.
따라서 ch - 'a'를 계산하면:
'a' - 'a' = 0
'b' - 'a' = 1
'c' - 'a' = 2
...
'z' - 'a' = 25
이렇게 ch - 'a'의 결과는 해당 문자에 대응하는 charCounts 배열의 인덱스가 되는 거다.
++는 해당 인덱스의 값을 1 증가시켜서 해당 문자가 한 번 더 등장했음을 기록하는 거다.
int maxCount = -1; char mostFrequentChar = ' ';:
이제 모든 문자의 횟수를 세었으니, 가장 많이 나온 문자를 찾한다.
maxCount는 지금까지 발견된 문자 중 가장 높은 등장 횟수를 저장할 변수이다.
단어에는 최소 한 글자는 있을 것이고, 한 번은 등장하므로 -1로 초기화하면 첫 번째 문자의 횟수와 비교했을 때 항상 maxCount가 갱신될 거다.
mostFrequentChar는 가장 많이 등장한 문자를 저장할 변수이다.
for (int i = 0; i < 26; i++) { ... }:
charCounts 배열 전체를 순회하면서 어떤 알파벳이 가장 많이 등장했는지 확인한다.
i는 0부터 25까지 증가하며, 이는 'a'부터 'z'까지의 각 알파벳을 나타낸다.
if (charCounts[i] > maxCount) { ... }:
charCounts[i]는 현재 i번째 알파벳(예: i가 0이면 'a', i가 1이면 'b')의 등장 횟수이다.
이 횟수가 현재 maxCount보다 크다면, 새로운 최다 등장 문자를 찾았다는 의미이다.
maxCount = charCounts[i]; mostFrequentChar = (char) ('a' + i);:
maxCount를 현재 문자의 횟수로 갱신한다.
mostFrequentChar는 현재 i에 해당하는 문자로 갱신해야 한다.
i는 인덱스(0부터 25)이므로, ('a' + i)를 계산하면 다시 문자로 변환된다.
예를 들어, i가 0이면 ('a' + 0)은 'a'가 되고, i가 1이면 ('a' + 1)은 'b'가 된다.
이렇게 찾은 문자를 mostFrequentChar에 저장하는 거다.
System.out.println(mostFrequentChar + " " + maxCount);:
모든 반복이 끝나면, mostFrequentChar에는 가장 많이 등장한 알파벳이, maxCount에는 그 횟수가 저장되어 있을 거다.
이 둘을 공백으로 구분해서 출력한다.
br.close();:
BufferedReader를 사용한 후에는 반드시 close() 메소드를 호출하여 스트림을 닫고 시스템 자원을 해제해야 한다.
코드로 구현
package baekjoon.baekjoon_32;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
// 백준 15238번 문제
public class Main1276 {
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
// 첫 번째 줄의 단어 길이는 실제 로직에서 사용되지 않으므로 읽기만 하고 넘어갑니다.
int wordLength = Integer.parseInt(br.readLine());
// 두 번째 줄의 해적 단어를 읽습니다.
String pirateWord = br.readLine();
// 알파벳 'a'부터 'z'까지의 출현 횟수를 저장할 배열을 만듭니다.
// 총 26개의 칸이 필요하며, 각 인덱스는 'a'(0)부터 'z'(25)에 해당합니다.
int[] charCounts = new int[26];
// 단어의 각 문자를 순회하며 출현 횟수를 셉니다.
for (int i = 0; i < wordLength; i++) {
char ch = pirateWord.charAt(i); // 현재 문자를 가져옵니다.
charCounts[ch - 'a']++; // 'a'를 빼서 0부터 시작하는 인덱스로 변환 후 해당 인덱스의 카운트를 증가시킵니다.
}
// 가장 많이 등장한 문자와 그 횟수를 찾기 위한 변수를 초기화합니다.
int maxCount = -1; // 최다 등장 횟수를 저장할 변수 (최소 1번은 등장할 것이므로 -1로 초기화)
char mostFrequentChar = ' '; // 최다 등장 문자를 저장할 변수
// charCounts 배열을 순회하며 최다 등장 문자를 찾습니다.
for (int i = 0; i < 26; i++) {
// 현재 문자의 등장 횟수가 지금까지의 최대 횟수보다 크다면
if (charCounts[i] > maxCount) {
maxCount = charCounts[i]; // maxCount 변수를 현재 문자의 등장 횟수로 갱신합니다.
mostFrequentChar = (char) ('a' + i); // 해당 인덱스(i)를 다시 문자로 변환하여 저장합니다.
// (0 -> 'a', 1 -> 'b', ...)
}
}
// 결과를 출력합니다.
System.out.println(mostFrequentChar + " " + maxCount);
br.close(); // BufferedReader를 닫아 자원을 해제합니다.
}
}
코드와 설명이 부족할수 있습니다. 코드를 보시고 문제가 있거나 코드 개선이 필요한 부분이 있다면 댓글로 말해주시면 감사한 마음으로 참고해 코드를 수정 하겠습니다.