본문 바로가기
프로그래머스/Lv.2

[C++] 프로그래머스 오픈채팅방

by MINU.SHINNNN 2023. 3. 3.

https://school.programmers.co.kr/learn/courses/30/lessons/42888

 

프로그래머스

코드 중심의 개발자 채용. 스택 기반의 포지션 매칭. 프로그래머스의 개발자 맞춤형 프로필을 등록하고, 나와 기술 궁합이 잘 맞는 기업들을 매칭 받으세요.

programmers.co.kr

풀이

채팅방 출입 또는 닉네임 변경 정보가 담긴 record 벡터가 들어올 때, id에 따라 최종 닉네임을 저장하고 커맨드(Enter 또는 Leave)에 따라 출력해주면 되는 문제이다.

1. 공백이 포함된 문자열로 들어오기 때문에 stringstream을 사용해 분리한다.

2. id를 키로 가지는 해시를 사용해서 중복없이 최종 닉네임을 저장하도록 한다. 이 때, Leave 일 때는 name이 공백이므로 무시해야한다.

3. 큐에 id와 커맨드를 순서대로 담아둔다.

4. 해싱이 끝나면 큐를 돌면서 id에 저장된 닉네임과 명령에 따라 순서대로 answer에 답을 추가한다.

#include <string>
#include <vector>
#include <unordered_map>
#include <queue>
#include <sstream>
#include <iostream>

using namespace std;
// 큐로 가지고 있고, 아이디별 최종 이름은 해시에 저장
vector<string> solution(vector<string> record) {
    vector<string> answer;
    // id 별 최종 이름 저장 해시
    // key: id, value : name
    unordered_map<string, string> id_hash;
    // id, 명령 저장 큐
    queue<pair<string, string>> q;
    for (int i=0; i<record.size(); i++) {
        string cmd="", id="", name="";
        stringstream ss;
        ss.str(record[i]);
        ss >> cmd;
        ss >> id;
        ss >> name;
        
        // Leave 일때는 name이 공백이므로 바꾸면 안됨
        if (cmd == "Change" || cmd == "Enter") {
            id_hash[id] = name;
        }
        q.push({id, cmd});
    }
    
    while (!q.empty()) {
        pair<string, string> v = q.front();
        q.pop();
        string s="";
        s+=id_hash[v.first];
        if (v.second == "Enter") {
            s+="님이 들어왔습니다.";
            answer.push_back(s);
        }
        else if (v.second == "Leave") {
            s+="님이 나갔습니다.";
            answer.push_back(s);
        }
        s="";
    }
    return answer;
}