모든 예외를 잡는 C ++ … } catch (Throwable

Java와 동등한 C ++이 있습니까?

try {
    ...
}
catch (Throwable t) {
    ...
}

기본 Windows 기능을 호출하는 Java / jni 코드를 디버깅하려고하는데 가상 시스템이 계속 충돌합니다. 네이티브 코드는 단위 테스트에서 잘 보이고 jni를 통해 호출 할 때만 충돌하는 것 같습니다. 일반적인 예외 포착 메커니즘은 매우 유용합니다.



답변

try{
    // ...
} catch (...) {
    // ...
}

모든 C ++ 예외를 포착하지만 나쁜 디자인으로 간주해야합니다. c ++ 11의 새로운 current_exception 메커니즘을 사용할 수 있지만 c ++ 11 (재 작성이 필요한 레거시 코드 시스템)을 사용할 수 없으면 메시지 나 이름을 얻는 데 사용할 명명 된 예외 포인터가 없습니다. . 포착 할 수있는 다양한 예외에 대해 별도의 catch 절을 추가하고 맨 아래에있는 모든 항목 만 포착하여 예기치 않은 예외를 기록 할 수 있습니다. 예 :

try{
    // ...
} catch (const std::exception& ex) {
    // ...
} catch (const std::string& ex) {
    // ...
} catch (...) {
    // ...
}

답변

누군가는 C ++ 코드에서 “크래쉬”를 잡을 수 없다고 덧붙여 야한다. 그들은 예외를 던지지 않지만 좋아하는 것을합니다. 널 포인터 역 참조로 인해 프로그램이 중단되면 정의되지 않은 동작을 수행하는 것입니다. 없습니다std::null_pointer_exception . 예외를 잡으려고해도 도움이되지 않습니다.

누군가 가이 스레드를 읽고 프로그램 충돌의 원인을 얻을 수 있다고 생각하는 경우를 대비하여. 대신 gdb와 같은 디버거를 사용해야합니다.


답변

catch(...)GCC를 사용하여 필요한 경우 예외 유형을 내부에서 리버스 엔지니어링 할 수있는 방법입니다 (타사 라이브러리에서 알 수없는 경우 유용 할 수 있음).

#include <iostream>

#include <exception>
#include <typeinfo>
#include <stdexcept>

int main()
{
    try {
        throw ...; // throw something
    }
    catch(...)
    {
        std::exception_ptr p = std::current_exception();
        std::clog <<(p ? p.__cxa_exception_type()->name() : "null") << std::endl;
    }
    return 1;
}

부스트 를 사용할 여유가 있다면 캐치 섹션을 더 간단하게 (외부에서) 크로스 플랫폼으로 만들 수 있습니다

catch (...)
{
    std::clog << boost::current_exception_diagnostic_information() << std::endl;
}

답변

try {
   // ...
} catch (...) {
   // ...
}

참고 그 ...안에catch 즉, 실제 줄임표이다. 세 개의 점.

그러나 C ++ 예외는 반드시 기본 Exception클래스의 서브 클래스 일 필요 는 없으므로이 구문을 사용할 때 발생하는 예외 변수를 실제로 볼 수있는 방법은 없습니다.


답변

모든 예외를 이식 가능한 방식으로 잡을 수는 없습니다 (C ++에서). 일부 예외는 C ++ 컨텍스트에서 예외가 아니기 때문입니다. 여기에는 0으로 나누기 오류 및 기타 항목이 포함됩니다. 이러한 오류가 발생할 때 해킹하여 예외를 던질 수는 있지만, 쉽게 수행 할 수없고 이식 가능한 방식으로 올바르게 얻는 것은 쉽지 않습니다.

모든 STL 예외를 잡으려면 할 수 있습니다

try { ... } catch( const std::exception &e) { ... }

을 사용하면 e.what()을 반환 const char*하여 예외 자체에 대해 더 많이 알 수 있습니다. 이것은 당신이 가장 많이 요구 한 Java 구조와 유사한 구조입니다.

누군가가 상속받지 않은 예외를 던질만큼 바보 인 경우에는 도움이되지 않습니다 std::exception.


답변

요컨대을 사용하십시오 catch(...). 그러나 기본적으로 다음 catch(...)과 함께 사용됩니다 throw;.

try{
    foo = new Foo;
    bar = new Bar;
}
catch(...)       // will catch all possible errors thrown. 
{
    delete foo;
    delete bar;
    throw;       // throw the same error again to be handled somewhere else
}

이것이 올바른 사용 방법 catch(...)입니다.


답변

다음과 같이 작성하면됩니다 :

try
{
  //.......
}
catch(...) // <<- catch all
{
  //.......
}

그러나 여기에는 눈에 띄지 않는 위험이 있습니다. try블록 에 발생한 정확한 유형의 오류를 찾을 수 없으므로 catch예외 유형에 관계없이 프로그램이 지속되어야한다는 것을 확신 할 때이 유형을 사용 하십시오 catch블록에 정의 된 방식으로 .