예외 안정성 확보(effective C++ 29)

2015. 9. 4. 17:39프로그래밍/Effective C++

728x90
728x90

예외 안정성

요구사항

- 자원이 새도록 만들지 않는다.(함수 내부에서 동적할당한 후 해제하지 않고 탈출하는 경우)

- 자료구조가 더럽혀지는 것을 허용하지 않는다.(정상적인 동작을 예상하고 카운트 등을 증가시켰는데, 

예상치 못한 예외에 의해 함수에서 탈출해버리는 경우)


보장성

예외 안전성을 가진 함수는 아래의 세 가지 보장(Guarantee) 중 하나를 제공한다.

- 기본적인 보장(Basic Guarantee) : 함수 동작 중 예외가 발생하면, 실행 중인 프로그램에 관련된 모든 것들을 

유효한 상태로 유지한다. 

- 강력한 보장(Strong Guarantee) : 프로그램의 상태를 절대로 변경하지 않는다는 보장. 

호출이 실패하면 호출 자체를 없었던 것처럼 하여 프로그램의 상태가 되돌아간다.

- 예외불가 보장(Nothrow Guarantee) : 예외를 절대로 던지지 않겠다는 보장. 

약속한 동작은 언제나 끝까지 완수하는 함수


기본적인 보장

- 함수 동작 중에 예외가 발생하면 실행 중인 프로그램에 관련된 모든 것들이 유효한 상태로 유지하겠다는 보장.

- 모든 객체의 상태는 내부적으로 일관성을 유지하고 있다.

- 프로그램의 상태가 정확히 어떤지 예측이 안 될 수도 있다. 이는 전적으로 함수를 만든 사람의 책임이다.



강력한 보장

- 예외가 발생하면 프로그램의 상태를 절대로 변경하지 않겠다는 보장.

- 호출이 성공하면 마무리까지 완벽하게 성공하고

실패하면 함수 호출이 없었던 것처럼 프로그램의 상태가 되돌아 간다.


- 복사-후-맞바꾸기 방법으로 구현 할 수 있지만 모든 함수에 대해 실용적인 것은 아니다.

(안정성을 보장하지만 속도면에서는 실용적이지 않을 수 있다.)

복사-후-맞바꾸기 : 객체를 수정하고 싶으면 객체의 사본을 하나 만들어 놓고 그 사본을 수정하는 것

수정 동작 중 실행되는 연산에서 예외가 던져져도 원본 객체는 바뀌지 않는다.

필요한 동작이 전부 성공적으로 완료되면 수정된 객체를 원본 객체와 맞바꾼다.


- 실용적이지 않은 이유는 객체를 복사하여 스왑하는데 발생하는 비용과

강력한 보장을 제공하려는 함수 내부에서 다른 함수를 호출할 경우 각 함수간의 부수효과가 발생하여

이를 모두 감안해서 제공하기 때문이다.




예외 불가 보장

- 예외를 절대로 던지지 않겠다는 보장. 약속한 동작은 끝까지 완수한다.

- 연산시 절대로 실패하지 않는다는 것을 보장하는 것이다. (예: 기본형 int)

- 강력한 보장, 기본 보장은 소멸자가 예외 불가라는 가정에 의존한다.


정리

- 예외 안전성을 갖춘 함수는 실행 중 예외가 발생하더라도 자원을 누출시키지 않으며, 

자료구조를 더럽힌 채로 내버려 두지 않는다.

이런 함수들이 제공할 수 있는 안전성 보장은 기본적인 보장, 강력한 보장, 예외 금지 보장이 있다.


- 강력한 예외 안전성 보장은 ‘복사-후-맞바꾸기’ 방법을 써서 구현할 수 있지만,

모든 함수에 대해 강력한 보장이 실용적인 것은 아니다.


- 어떤 함수가 제공하는 예외 안전성 보장의 강도는,

그 함수가 내부적으로 호출하는 함수들이 제공하는 가장 약한 보장을 넘지 않는다.



728x90
반응형