답변:
std::terminate()
어떤 스레드에서든 호출 할 수 있으며 참조하는 스레드가 강제 종료됩니다.
당신은을 준비 할 수 ~thread()
개입하지 않고, 타겟 thread의 개체에 실행하는 join()
나 detach()
그 객체에. 옵션 1과 동일한 효과가 있습니다.
예외를 발생시키는 소멸자가있는 예외를 디자인 할 수 있습니다. 그런 다음 강제 종료 될 때 대상 스레드가이 예외를 처리하도록 배열하십시오. 이것의 까다로운 부분은 대상 스레드 가이 예외를 발생시키는 것입니다.
옵션 1과 2는 프로세스 내 리소스를 누출시키지 않지만 모든 스레드 를 종료 합니다 .
옵션 3은 아마도 리소스를 유출하지만 대상 스레드가 예외를 처리하는 데 동의해야하기 때문에 부분적으로 협력 적입니다.
C ++ 11에는 다중 스레드 프로그램에서 단일 스레드를 비협조적으로 죽이는 (즉, 모든 스레드를 죽이지 않고) 이식 할 수있는 방법이 없습니다. 이러한 기능을 디자인하려는 동기는 없었습니다.
A std::thread
는이 멤버 함수를 가질 수 있습니다.
native_handle_type native_handle();
이것을 사용하여 원하는 작업을 수행하기 위해 OS 종속 함수를 호출 할 수 있습니다. 예를 들어 Apple OS에서이 기능은 존재하며 native_handle_type
입니다 pthread_t
. 성공하면 리소스가 유출 될 수 있습니다.
std::terminate
정적 소멸자를 호출하거나 출력 버퍼를 플러시하지 않으므로 리소스가 해제되는 순서가 잘 정의되어 있지 않거나 데이터가 사용자에게 표시되거나 영구 저장소에 기록되거나 심지어 일관되고 완전합니다.
exit()
하거나 abort()
동일한 전체 효과를 낼 수도 있습니다 .
@Howard Hinnant의 답변은 정확 하고 포괄적입니다. 그러나 std::terminate()
(전체 프로세스) @AlexanderVX가 생각한 "종료"와 동일한 이름을 갖기 때문에 너무 빨리 읽으면 잘못 이해할 수 있습니다 (1 스레드).
요약 : "1 스레드 + 강제 종료 (타겟 스레드가 협력하지 않음) + 순수 C ++ 11 = 안됩니다."
std::terminate()
대답은 고전적인 장난스러운 Djinn 이야기와 같습니다. 그것은 그가 의도 한 방식이 아니더라도 OP에 대한 서한에 대한 모든 것을 이행한다 . 절제된 유머가 나를 웃게 만들었습니다. :-)
이 질문은 실제로 멀티 스레딩 개념에 대한보다 깊은 이해와 올바른 이해를 바탕으로이 주제에 대한 통찰력을 제공합니다. 실제로 비동기 스레드를 사용하지 말라고 경고하지 않고 갑자기 스레드를 종료하는 기능을 제공하는 언어 나 운영 체제가 없습니다. 그리고 이러한 모든 실행 환경은 개발자에게 강력하게 조언하거나 협력 또는 동기식 스레드 종료를 기반으로 빌드 멀티 스레딩 응용 프로그램을 요구합니다. 이 일반적인 결정과 조언의 이유는 모두 동일한 일반 멀티 스레딩 모델을 기반으로하기 때문입니다.
멀티 프로세싱과 멀티 스레딩 개념을 비교하여 두 번째 개념의 장단점을보다 잘 이해하겠습니다.
멀티 프로세싱은 전체 실행 환경을 운영 체제에서 제어하는 완전히 격리 된 프로세스 세트로 분할한다고 가정합니다. 프로세스는 프로세스의 로컬 메모리와 프로세스 내부의 데이터 및 파일, 소켓, 동기화 개체와 같은 모든 시스템 리소스를 포함하여 실행 환경 상태를 통합하고 격리합니다. 격리는 프로세스 경계에 의한 결함 전파를 제한하기 때문에 프로세스의 매우 중요한 특성입니다. 즉, 어떤 프로세스도 시스템에서 다른 프로세스의 일관성에 영향을 줄 수 없습니다. 프로세스 동작에 대해서도 마찬가지이지만 덜 제한적이고 흐리게 처리됩니다. 이러한 환경에서는 모든 프로세스가 임의의 "임의"순간에 종료 될 수 있습니다.
반대로 멀티 스레딩은 동일한 프로세스에서 여러 스레드를 실행한다고 가정합니다. 그러나이 모든 스레드는 동일한 격리 상자를 공유하며 프로세스의 내부 상태에 대한 운영 체제 제어가 없습니다. 결과적으로 모든 스레드는 전역 프로세스 상태를 변경하고 손상시킬 수 있습니다. 동시에 스레드의 상태가 스레드를 완전히 죽이기에 안전한 것으로 알려진 지점은 응용 프로그램 논리에 따라 다르며 운영 체제 나 프로그래밍 언어 런타임에 대해서는 알려지지 않았습니다. 결과적으로 임의의 순간에 스레드 종료는 실행 경로의 임의의 지점에서 스레드를 종료하는 것을 의미하며 프로세스 전체의 데이터 손상, 메모리 및 핸들 누수로 쉽게 이어질 수 있습니다.
이 때문에 일반적인 접근 방식은 개발자가 동기식 또는 협업 스레드 종료를 구현하도록하는 것입니다. 여기서 하나의 스레드가 다른 스레드 종료를 요청할 수 있고 잘 정의 된 지점의 다른 스레드가이 요청을 확인하고 잘 정의 된 상태에서 종료 절차를 시작할 수 있습니다 안전하고 일관된 방식으로 모든 글로벌 시스템 전체 리소스 및 로컬 프로세스 전체 리소스를 공개합니다.
OS 종속 함수를 사용하여 C ++ 스레드를 종료하는 팁 :
std::thread::native_handle()
단지 호출하기 전에 스레드의 유효 기본 핸들 타입을 얻을 수 있습니다 join()
또는 detach()
. 그 후 native_handle()
0을 반환합니다- pthread_cancel()
코어 덤프됩니다.
기본 스레드 종료 기능 (예 :)을 효과적으로 호출하려면 또는 pthread_cancel()
을 호출하기 전에 기본 핸들을 저장해야합니다 . 따라서 네이티브 터미네이터에는 항상 유효한 유효한 네이티브 핸들이 있습니다.std::thread::join()
std::thread::detach()
자세한 설명은 http://bo-yang.github.io/2017/11/19/cpp-kill-detached-thread 를 참조하십시오 .
종료 해야하는 스레드가 모든 종류의 대기 모드이거나 무거운 작업을 수행하고 있다고 생각합니다. "순진한"방법을 사용하는 것이 좋습니다.
전역 부울을 정의하십시오.
std::atomic_bool stop_thread_1 = false;
스레드가 자연스럽게 종료 될 때까지 호출 스택의 모든 함수가 리턴되도록 다음 키 포인트 (또는 이와 유사한 코드)를 여러 키 포인트에 넣으십시오.
if (stop_thread_1)
return;
그런 다음 다른 (주) 스레드에서 스레드를 중지하십시오.
stop_thread_1 = true;
thread1.join ();
stop_thread_1 = false; //(for next time. this can be when starting the thread instead)