[Effective C++] 50. new 및 delete를 언제 바꿔야 좋은 소리를 들을지 파악해 두자
일반적으로 컴파일러가 제공하는 operator new, operator delete는 대체로 쓸만하다. 그리고 사용자가 오버로딩을 통해 재정의한다면 수동으로 지정해줄 관례들이 있다.
따라서 기본 operator의 new와 delete를 사용해도 무관하지만 사용자가 본인의 프로젝트에 알맞은 오버로딩을 구현한다면 훨씬 효율적인 operator new , operator delete가 탄생할 수도 있는데 언제 operator new, delete를 바꾸어야 하는 지 알아보자.
사용자 정의 new와 delete를 고려해야 할 때
1. 잘못된 힙 사용을 탐지하기 위해
new 한 메모리에 delete 하는 것을 잊어버리면 메모리 누출이 되고, 이미 메모리 해제한 메모리를 또 메모리 해제한다면 프로그램은 터질 것이다. 만약 할당된 메모리 주소의 목록을 operator new가 유치해 두고 operator delete가 그 목록으로부터 주소를 하나씩 제거해 주게 만들어져 있다면, 이런 실수는 예방할 수 있다.
실수를 하다 보면 데이터 오버런(overrun)과 데이터 언더런(underrun)이 발생할 수 있다.
오버런 : 할당된 메모리 블록의 끝을 넘어 뒤에 메모리를 할당하는 것
언더런 : 할당된 메모리 블록의 시작을 넘어 앞에 메모리를 할당하는 것
요구된 크기보다 약간 더 메모리를 할당한 후에 사용자가 실제로 사용할 메모리의 앞과 뒤에 오버런/언더런 탐지용 바이트 패턴을 적어두도록 만들면 오버런과 언더런을 예방할 수 있다.
2. 효율을 향상시키기 위해
컴파일러가 제공하는 operator new와 operator delete 함수는 일반적인 쓰임새에 맞춰 설계된 것이다.
일반적인 쓰임새에 초점을 맞췄기에 사용자에 최적화됐다고는 할 수 없다. new와 delete를 사용자 정의 버전으로 바꾸는 것만으로 성능 향상을 기대해 볼 수 있다.
3. 동적 할당 메모리의 실제 사용에 관한 통계 정보를 수집하기 위해
사용자 정의 operator new와 operator delete를 사용하면 메모리가 할당되고 해제되는 순서(FIFO, LIFO), 메모리 블록의 분포 등 의 정보를 아주 쉽게 수집할 수 있다.
4. 기본 메모리 관리자의 공간 오버헤드를 줄이기 위해
범용 메모리 관리자는 사용자 정의 버전과 비교해서 속력이 느린 경우도 많고, 메모리도 많이 잡아먹는 사례가 많다.
할당된 각각의 메모리 블록에 대해 전체적으로 지우는 부담이 꽤 되기 때문이다. 크기가 작은 객체에 대해 튜닝된 할당자를 사용하면 오버헤드를 실질적으로 제거할 수 있다.
5. 적당히 타협한 기본 할당자의 바이트 정렬 동작을 보장하기 위해
64bit 아키텍처에서는 double이 8byte 단위로 정렬되어 있을 때 읽기, 쓰기 속도가 가장 빠르다. 하지만 소수 몇몇 컴파일러는 operator new 함수가 double에 대한 동적 할당 시에 8byte 정렬을 보장하지 않는 것들이 있다. 이런 경우 기존 operator new 대신 8byte 정렬을 보장하는 사용자 정의 버전으로 바꾸면 성능을 올릴 수 있다.
6. 임의의 관계를 맺고 있는 객체들을 한 군데에 나란히 모아 놓기 위해
페이지 부재(page fault) 발생 횟수를 최소화하고 싶을 때, 해당 자료구조를 담을 별도의 힙을 생성함으로써 이들이 가능한 한 적은 페이지를 차지하도록 하면 효과를 볼 수 있다. 이러한 메모리 군집화는 new 및 위치 지정 delete를 통해 쉽게 구현할 수 있다.
7. 그때그때 원하는 동작을 수행하도록 하기 위해
기존 컴파일러의 operator new와 operator delete가 하지 않는 일을 해주었으면 할 때 사용할 수 있다. 예를 들면 메모리 할당과 해제를 공유 메모리에다가 하고 싶은데 공유 메모리를 조작하는 일은 C API로 밖에 할 수 없을 때 사용자 정의 버전을 만들면 가능하다.(52장 참고)
또 다른 예로는 데이터의 보안 강화를 위해 해제한 메모리 블록에 0을 덮어쓰는 사용자 정의 operator delete를 만드는 경우도 생각해 볼 수 있다.
요약
- 개발자가 스스로 사용자 정의 new 및 delete를 작성하는 데는 여러 가지 나름대로 타당한 이유가 있다. 여기에는 수행 성능을 향상시키려는 목적, 힙 사용 시의 에러를 디버깅하려는 목적, 힙 사용 정보를 수집하려는 목적 등이 포함된다.
'Books > Effective C++' 카테고리의 다른 글
[Effective C++] 52. 위치지정 new를 작성한다면 위치지정 delete도 같이 준비하자 (0) | 2022.07.24 |
---|---|
[Effective C++] 51. new 및 delete를 작성할 때 따라야 할 기존의 관례를 잘 알아 두자 (0) | 2022.07.23 |
[Effective C++] 49. new 처리자의 동작 원리를 제대로 이해하자 (0) | 2022.07.16 |
[Effective C++] 48. 템플릿 메타프로그래밍, 하지 않겠는가? (0) | 2022.07.16 |
[Effective C++] 47. 타입에 대한 정보가 필요하다면 특성정보 클래스를 사용하자 (0) | 2022.07.15 |
댓글
이 글 공유하기
다른 글
-
[Effective C++] 52. 위치지정 new를 작성한다면 위치지정 delete도 같이 준비하자
[Effective C++] 52. 위치지정 new를 작성한다면 위치지정 delete도 같이 준비하자
2022.07.24 -
[Effective C++] 51. new 및 delete를 작성할 때 따라야 할 기존의 관례를 잘 알아 두자
[Effective C++] 51. new 및 delete를 작성할 때 따라야 할 기존의 관례를 잘 알아 두자
2022.07.23 -
[Effective C++] 49. new 처리자의 동작 원리를 제대로 이해하자
[Effective C++] 49. new 처리자의 동작 원리를 제대로 이해하자
2022.07.16 -
[Effective C++] 48. 템플릿 메타프로그래밍, 하지 않겠는가?
[Effective C++] 48. 템플릿 메타프로그래밍, 하지 않겠는가?
2022.07.16