프로그래밍C++ 멀티스레드/서버 개발자

C++에서 멀티스레딩 작업 시 고려해야 할 사항은 무엇인가요? std::mutex, std::lock_guard, std::unique_lock의 차이점을 설명하고 스레드 안전한 작업의 예를 제시하세요.

Hintsage AI 어시스턴트로 면접 통과

답변

최신 C++ (C++11부터)에서는 멀티스레딩 작업을 위한 풍부한 도구가 존재합니다: std::thread, 뮤텍스 및 리소스 접근을 관리하기 위한 다양한 래퍼 객체. 스레드 간 안전한 상호작용은 다음 구성 요소를 이해해야 합니다:

  • std::mutex — 접근 동기화를 위한 기본 잠금 원시 요소. 명시적인 lock/unlock이 필요합니다.
  • std::lock_guard — RAII 래퍼로, 스코프 진입/이탈 시 자동으로 뮤텍스를 획득하고 해제합니다.
  • std::unique_lock — 더 유연한 RAII 래퍼로, 잠금을 수동으로 하고 해제하며, 뮤텍스 소유권을 스레드 간 이동하고 condition_variable을 사용할 수 있습니다.

경쟁 상태를 피하기 위해 가능할 때마다 RAII 래퍼를 사용하십시오. 동일한 뮤텍스를 반복적으로 획득하려고 하면 데드락이 발생합니다(재귀 뮤텍스가 아닌 경우).

올바른 작업 예:

#include <iostream> #include <mutex> #include <thread> std::mutex mtx; void printThreadSafe(int id) { std::lock_guard<std::mutex> lock(mtx); std::cout << "스레드 " << id << std::endl; } int main() { std::thread t1(printThreadSafe, 1); std::thread t2(printThreadSafe, 2); t1.join(); t2.join(); }

트릭 질문

std::lock_guardstd::mutex를 사용하여 std::condition_variable로 조건 동기화를 구현할 수 있습니까?

답변: 아니요! std::condition_variable 작업을 위해서는 반드시 std::unique_lockstd::mutex가 필요합니다. lock_guard는 잠금을 제어할 수 있는 메서드를 제공하지 않기 때문에(예: 일시적으로 해제하고 다시 획득하는 unlock) 알림을 기다릴 때 필요합니다.

예:

std::mutex mtx; std::condition_variable cv; bool ready = false; void waitForEvent() { std::unique_lock<std::mutex> lock(mtx); cv.wait(lock, []{return ready;}); // 추가 처리 }

주제에 대한 세부 사항을 알지 못해 발생한 실제 오류 예


이야기

프로젝트에서 수동으로 mtx.lock()/mtx.unlock()을 사용했습니다. lock/unlock 사이에 예외가 발생하면 뮤텍스가 잠긴 채로 남아 많은 스레드가 "멈춤" 상태가 되었습니다. RAII(std::lock_guard)로 변경하니 문제는 사라졌습니다.


이야기

std::condition_variable을 통해 알림을 줄 때 std::unique_lock 대신 std::lock_guard를 사용했습니다. 결과적으로, 프로그램은 새로운 컴파일러에서 컴파일되지 않았고, 구 버전에서는 API 불일치로 인해 런타임 단언이 발생했습니다.


이야기

코드에서 std::lock_guard의 unlock()을 호출하여 뮤텍스 접근을 "수동적으로" 제어했습니다. 이는 다양한 컴파일러에서 정의되지 않은 동작으로 이어졌고, 때로는 애플리케이션이 중단되었습니다. lock_guard가 수동 해제를 지원하지 않음을 깨닫고 unique_lock으로 마이그레이션이 필요했습니다.