출처: https://school.programmers.co.kr/learn/courses/30/lessons/12951#
문제 설명
JadenCase란 모든 단어의 첫 문자가 대문자이고, 그 외의 알파벳은 소문자인 문자열입니다. 단, 첫 문자가 알파벳이 아닐 때에는 이어지는 알파벳은 소문자로 쓰면 됩니다. (첫 번째 입출력 예 참고)
문자열 s가 주어졌을 때, s를 JadenCase로 바꾼 문자열을 리턴하는 함수, solution을 완성해주세요.
제한 조건
s는 길이 1 이상 200 이하인 문자열입니다.
s는 알파벳과 숫자, 공백문자(" ")로 이루어져 있습니다.
숫자는 단어의 첫 문자로만 나옵니다.
숫자로만 이루어진 단어는 없습니다.
공백문자가 연속해서 나올 수 있습니다.
입출력 예
s return
"3people unFollowed me" "3people Unfollowed Me"
"for the last week" "For The Last Week"
※ 공지 - 2022년 1월 14일 제한 조건과 테스트 케이스가 추가되었습니다.
내가 작성한 코드문
class Solution {
public String solution(String s) {
String answer = "";
// 첫 문자가 대문자이고, 그 외의 알파벳은 소문자인 문자열
// 단, 첫 문자가 알파벳이 아닐 때에는 이어지는 알파벳은 소문자로 쓰면 됩니다.
// String [] arr = s.split(" ");// 스트링 배열에 저장
StringBuilder sb = new StringBuilder();
boolean isFirst = true;
for(char c : s.toCharArray()){
if(c == ' '){
sb.append(c);
isFirst = true;
} else if(isFirst){
sb.append(Character.toUpperCase(c));
isFirst = false;
} else {
sb.append(Character.toLowerCase(c));
} // 공백 만나면 다음 글자는 단어 첫 글자
}
// for(int i = 0; i < arr.length; i++){
// // 배열의 첫 단어를 대문자로 변경
// char b = arr[i].charAt(0);
// if(Character.isLowerCase(b)){
// arr[i] = Character.toUpperCase(b) + arr[i].substring(1);
// } else {
// arr[i] = b + arr[i].substring(1);
// }
// if(i == (arr.length - 1)){
// answer += arr[i] + "";
// } else {
// answer += arr[i] + " ";
// }
// }
return sb.toString();
}
}
우선 "JadenCase" 문제는 단어 구분뿐 아니라 "공백의 위치와 개수를 그대로 유지"해야한다.
String[] arr = s.split(" ");
이 코드문을 쓸 경우에
공백을 split으로 처리하면 "공백을 재조합하는 과정이 엉켜" 버린다는 것이다.
그리고 원래 코드문에서
if(i == (arr.length - 1)){
answer += arr[i] + "";
} else {
answer += arr[i] + " ";
}
여기서 항상 "단어 뒤에 한 칸의 공백"을 추가하게 된다. 하지만 만약 빈 문자열인 ""이 arr[i]에 들어오면?
arr[1] = "" // 빈 문자열
이것도 뒤에 " " 붙이기 때문에 원래 공백 2개 → 1개로 줄어들게 된다.
그리고 또 하나의 문제
빈 문자열인 경우 arr[i].charAt(0)을 하면?
char b = arr[i].charAt(0); // arr[i] == ""일 때 → IndexOutOfBoundsException 발생!
결론은
split 사용은 위험 — 공백 재조합이 애매하고 빈 문자열 예외도 발생.
그래서 char 단위로 순회하면서:
단어의 시작인지 판별 (isFirst == true 일 때 대문자)
공백 나오면 isFirst = true로 바꿈
공백 그대로 추가
이 방식이 정석.
다른 사람의 풀이
class Solution {
public String solution(String s) {
String answer = "";
String[] sp = s.toLowerCase().split("");
boolean flag = true;
for(String ss : sp) {
answer += flag ? ss.toUpperCase() : ss;
flag = ss.equals(" ") ? true : false;
}
return answer;
}
}
import java.util.regex.*;
class Solution {
public String solution(String s) {
Matcher m = Pattern.compile("\\b([\\w])([\\w]*)").matcher(s);
while (m.find()) {
s = s.replaceAll("\\b" + m.group(), m.group(1).toUpperCase() + m.group(2).toLowerCase());
}
return s;
}
}
class Solution {
public String solution(String s) {
String answer = "";
boolean isFirst = true;
for(String data : s.toLowerCase().split("")){
answer += isFirst ? data.toUpperCase() : data;
isFirst = data.equals(" ") ? true : false;
}
return answer;
}
}```