thread


요즘은 고성능 프로그램을 만들때 멀티코어를 얼마나 잘 활용하느냐를 중요하게 여긴다. 그래서 다양한 프로그래밍 언어와 라이브러리가 병렬 프로그래밍을 지원한다.  C++11의 큰 특징중 하나는 역시 'thread'라이브러리의 지원이다.

C++11의 thread라이브러리를 사용하면 복잡하고 플랫폼마다 다르게 기술해야 하는 기존의 스레드 프로그래밍을 단순하면서도 플랫폼 독립적으로 구현할 수 있다.




스레드 만들기


#include <thread>



<스레드 만들기 예제>



쓰레드가 3개 만들어져서 실행되었지만, 공유 객체를 동기화하지 않아서 발생한 문제다. 이문제는 동기화를 통해 해결한다.







스레드가 종료될 때까지 기다리기


위 예제에서 에러가 발생하는 이유는 스레드가 아직 실행 중인데 프로그램이 종료되었기 때문이다. 이 버그를 해결하려면 thread 클래스의 join 함수를 사용하여 스레드의 실행이 끝날 때가지 기다리게 하면 된다. 




<join을 사용하여 스레드 종료 대기 예제>


join함수를 호출하여 스레드가 종료될 떄까지 기다린 후 프로그램을 종료한다.





<스레드 순차적으로 실행하기 예제>










스레드 식별자와 스레드 교환


get_id() 함수를 사용하면 스레드 클래스로 만들어진 스레드를 다른 스레드와 식별할 수 있다. 즉, 이것을 사용하면 멀티스레드에서 공요 리소스에 접근하는 스레드가 어떤 것인지 알 수 있어서 디버깅할 때나 공용 리소스 관리에 사용한다.


swap() 함수는 스레드 객체끼리 스레드를 교환할 떄 사용한다. 즉, STL 컨테이너의 swap과 같은 역할을 한다.




<스레드 식별과 교환 예제>



결과를 보면 swap을 하기전과 한 후의 식별자가 서로 바뀐것을 알 수 있다.







스레드 때어내기와 스레드 종료 대기 가능 조사


detach 함수는 스레드 객체에 연결된 스레드 연결고리를 떼어낸다. 따라서   detach함수를 호출한 후에는 스레드 객체로 스레드를 제어할 수 없다. 그러나 detach를 호출했다고 해서 스레드가 실제로 종료되니ㅡㄴ 것이 아니라 단순히 스레드 객체와 스레드 간의 연결을 끊어주는 것이다.




<스레드 연결 해제하기 예제>


위 예제를 실행하면  join()함수를 호출하지 않다도 프로그램을 종료할 때 에러가 발생하지 않는다. 이것은 스레드 객체가 더는 스레드를 관리하지 않기 때문이다. 만약 위 예제에서  Thread.join()의 주석처리를 제거하고 호출하면 에러가 발생한다. 이유는 스레드 객체가 더는 스레드를 가지지 않는데  join함수를 호출했기 때문인다.



위와 같ㅌ은 에러를 막으려면 joinable 함수를 사용하여 스레드가 종료될 때까지 기다릴 수 있는지 조사한 후에 join함수를 호출하면 된다. 즉, joinable 함수를 호출하여 반환값이  true일 떄에만 join함수를 호출하면 이와 같은 에러를 막을 수 있다.




<joinable을 사용하여 스레드가 종료될지 조사 예제>








스레드 일시 중지 및 양보하기


sleep_for와 sleep_until 함수는 스레드를 일시 중지시킬 때 사용한다. 두 함수는 이름에서 알 수 있듯이 sleep_for는 특정 시간 동안 일시 중지 시키고 싶을 때 사용하고 sleep_until은 일정한 시간까지 중지시킬 때 사용한다. sleep_for와 sleep_until 함수는 std::thread의 멤버는 아니고 std::this_thread네임 스페이스에 속해 있다.



<sleep_for와 sleep_until 예제>





출처 : Thinking About C++ STL 프로그래밍 (최홍배 지음)



'C++ > STL' 카테고리의 다른 글

21. 동기화 객체1  (0) 2017.11.03
각 STL 컨테이너를 써야할 때를 정리(차이점)  (0) 2017.10.26
19. chrono  (0) 2017.10.25
18. unordered_map  (0) 2017.10.24
17. forward_list  (0) 2017.10.23

+ Recent posts