오늘은 오랜만에 프로그래머스의 오픈채팅방 문제의 후기를 남겨본다.
프로그래머스
코드 중심의 개발자 채용. 스택 기반의 포지션 매칭. 프로그래머스의 개발자 맞춤형 프로필을 등록하고, 나와 기술 궁합이 잘 맞는 기업들을 매칭 받으세요.
programmers.co.kr
문제
문제는 너무 길어서 위의 링크로 접근해주시면 됩니다!
입력
제한사항
- record는 다음과 같은 문자열이 담긴 배열이며, 길이는 1 이상 100,000 이하이다.
- 다음은 record에 담긴 문자열에 대한 설명이다.
- 모든 유저는 [유저 아이디]로 구분한다.
- [유저 아이디] 사용자가 [닉네임]으로 채팅방에 입장 - "Enter [유저 아이디] [닉네임]" (ex. "Enter uid1234 Muzi")
- [유저 아이디] 사용자가 채팅방에서 퇴장 - "Leave [유저 아이디]" (ex. "Leave uid1234")
- [유저 아이디] 사용자가 닉네임을 [닉네임]으로 변경 - "Change [유저 아이디] [닉네임]" (ex. "Change uid1234 Muzi")
- 첫 단어는 Enter, Leave, Change 중 하나이다.
- 각 단어는 공백으로 구분되어 있으며, 알파벳 대문자, 소문자, 숫자로만 이루어져있다.
- 유저 아이디와 닉네임은 알파벳 대문자, 소문자를 구별한다.
- 유저 아이디와 닉네임의 길이는 1 이상 10 이하이다.
- 채팅방에서 나간 유저가 닉네임을 변경하는 등 잘못 된 입력은 주어지지 않는다.
풀이
해당 문제는 records 배열을 사용해서 사용자가 어떤 id와 nickName으로 들어오는지 체크를 해서 마지막으로 방을 개설한 사람이 보게 되는 메세지를 출력하는 문제이다.
문제에서 닉네임을 변경하는 방법은 다음과 같이 두 가지가 있다.
- 채팅방을 나간 후(Leave), 새로운 닉네임으로 다시 들어간다(Enter).
- 채팅방에서 닉네임을 변경(Change)한다.
records 배열의 길이(1 <= records >= 100, 000) 가 10만 정도인 것을 보고 O(N ^ 2)는 힘들수도 있겠다고 생각을 하고 어떤 자료구조를 사용할지 생각을 했다.
사용자의 id에 대한 최신의 nickName을 key(id), value(nickName)을 가지면 되겠다고 생각을 했다.
우선, 가장 최신 사용자의 id, nickName을 가지고 오기 위해서 반복문을 돌면서 다음과 같이 진행했다.
Leave로 들어오면 사용자가 나가도 id에 대한 nickName을 출력해야해서 HashMap은 건드리지 않고 continue했다.
Enter로 들어오면 HashMap<String, String> idAndNickName에 새로운 id, nickName을 put(key, value) 해주고,
Change로 들어와도 put(key, value)로 수정해줬다.
이제는 아이디 별 닉네임이 담긴 맵을 가지고 있기에 records의 length만큼 반복문을 반복해줬다.
Enter, Leave 로 들어오면 ArrayList<String> answer에 현재 record의 userId에 대한 nickName으로 메시지를 add()해줬다.
마지막으로 String[] 배열을 리턴해야 했다. ArrayList<String> answer를 stream()으로 변경해서 toArray() 함수를 사용해서 String[] 배열로 리턴해줬다.
package level02.E03_오픈채팅방;
import java.util.*;
class Solution {
public String[] solution(String[] records) {
List<String> answer = new ArrayList<>();
HashMap<String, String> idAndNickName = new HashMap<>();
for (String record : records){
String[] splitRecord = record.split(" ");
String action = splitRecord[0];
// Leave 는 pass
if ("Leave".equals(action)){
continue;
}
String userId = splitRecord[1];
String nickName = splitRecord[2];
if ("Enter".equals(action)){
idAndNickName.put(userId, nickName);
}
if ("Change".equals(action)){
idAndNickName.put(userId, nickName);
}
}
for (String record : records){
String[] splitRecord = record.split(" ");
String action = splitRecord[0];
String userId = splitRecord[1];
if ("Enter".equals(action)){
answer.add(idAndNickName.get(userId) + "님이 들어왔습니다.");
}
if ("Leave".equals(action)){
answer.add(idAndNickName.get(userId) + "님이 나갔습니다.");
}
}
return answer.stream()
.toArray(arr -> new String[answer.size()]);
}
}
'코딩테스트 > Programmers' 카테고리의 다른 글
[SQL][PGS] 입양 시각 구하기(2) (0) | 2022.07.16 |
---|---|
[Programmers][Python][Level 1] [1차] 비밀지도 (0) | 2021.04.25 |
[Programmers][Python][Level 1] 짝수와 홀수 (0) | 2021.04.21 |
[Programmers][Python][Level 1] 제일 작은 수 제거하기 (0) | 2021.04.21 |
[Programmers][Python][Level 1] 나누어 떨어지는 숫자 배열 (0) | 2021.04.18 |
[Programmers][Python][Level 1] 내적 (0) | 2021.04.18 |
[Programmers][Python][Level 1] 음양 더하기 (0) | 2021.04.18 |
[Programmers][Python][Level 1] 예산 (0) | 2021.04.18 |