2014-06-24 2 views
0

예외와 관련된 문제가 발생했습니다. 코드는 다음과 같습니다catch (...)가 모든 예외를 catch하지 않음

,

try 
{ 
    auto it = set_difference(allInterfaces.begin(), allInterfaces.end(), eths.begin(), 
    eths.end(), newCards.begin()); 
} 
catch(...) 
{ 
    cout << "exception thrown << endl; 
} 

나는 예외가 있지만, 프로그램 종료와 예외를 catch하지 않는 catch 블록을 던지고있다() set_difference을 알고있다. 예외를 잡을 수있는 방법이 있습니까? 나는 모든 것이 항상 효과가 있어야한다고 생각했다.

도움 주셔서 감사합니다.

+0

'set_difference'가 던지는 예외는 무엇입니까? – Praetorian

+3

일부 예외는 * 예외라고하지만 C++ 예외가 아닌 시스템 (또는 프로세서) 예외임을 기억하십시오. 'catch' 블록은'throw'의 C++ 예외만을 잡아줍니다. 다른 종류의 예외 (예 : 널 포인터 접근으로 이어질 수도 있음)가 아닙니다. –

+0

벡터 newCards가 너무 작 으면 프로그램이 종료되었습니다. 이 오류가 있습니다 : *** glibc 감지 ***/네트워킹 : free() : 잘못된 포인터 : 0x000000000153d4a8 ***. 어쩌면 이것은 예외는 아닙니다. – Smithy

답변

2

set_difference은 입력 집합 중 하나에 고유 한 요소를 전달하는 출력 범위에 씁니다. 결과가 포함될 수있는 범위가 충분한 지 확인하는 것은 사용자의 책임입니다. 그렇지 않으면 범위 한계를 벗어나서 의 정의되지 않은 동작이 발생합니다. 이런 일이 발생해도 예외는 발생하지 않습니다. 최적의 표시기는 최적화되지 않은 빌드에서 어설 션이 실패한 것입니다. newCards 가정

이를 방지하는 가장 쉬운 방법은 객체가 할당 될 때마다 push_back를 호출합니다 std::back_insert_iterator을 사용하는 것입니다, push_back을 지원하는 컨테이너입니다. 사용할 수

auto it = set_difference(allInterfaces.begin(), allInterfaces.end(), 
         eths.begin(), eths.end(), std::back_inserter(newCards)); 

다른 옵션은 std::front_insert_iterator 있습니다 (push_front()를 호출)와 std::insert_iterator은 (insert()를 호출). 귀하의 필요에 가장 잘 맞는 것을 선택하십시오.

+0

고맙습니다. 그 멋진 솔루션입니다. – Smithy

1

주석의 도움을 받아 newCards.begin()에서 반환 된 반복기를 벡터의 범위를 넘어서 늘리거나 반복 할 가능성이 큽니다. 이로 인해 undefined behavior (경우에 따라 크래시가 발생 함)이 발생하고 throw 된 C++ 예외는 발생하지 않습니다. 반복자 액세스는 C++에서 경계 체크되지 않습니다 (거의없는 것들이 있습니다).

이 문제를 해결하려면 newCards 벡터의 끝 부분을 전달해야하며 범위를 벗어나지 않아야합니다.

+0

도와 주셔서 감사합니다. 이 문제가 발생하지 않게하려면 코드를 다시 디자인해야합니다. – Smithy

관련 문제