C ++ 0x에서 nullptr을 삭제하는 것이 여전히 안전합니까? 첫째, 두 문장 §5.3.5/2이 있습니다. 첫

에서 c++03이 널 포인터를 삭제하면 아무 효과가 없습니다 꽤 분명하다. 실제로 다음과 같이 명시 적으로 명시되어 있습니다 §5.3.5/2.

어느 쪽이든 delete 피연산자의 값이 널 포인터이면 연산이 영향을 미치지 않습니다.

그러나, 현재의 초안 에 대한 c++0x이 문장 누락 된 것으로 보인다. 나머지 초안에서는 delete-expression 의 피연산자가 널 포인터 상수가 아닌 경우 어떻게되는지 설명하는 문장 만 찾을 수있었습니다 . 에서 여전히 정의 된 널 포인터를 삭제하고 c++0x있습니까? 그렇다면 어디에 있습니까?

메모:

여전히 잘 정의되어 있음을 시사하는 중요한 상황 증거가 있습니다.

첫째, 두 문장 §5.3.5/2이 있습니다.

첫 번째 대안 (객체 삭제)에서 delete 피연산자의 값은 널 포인터 값일 수 있습니다.

두 번째 대안 (배열 삭제)에서 delete 피연산자의 값은 널 포인터 값이거나 …

이것들은 피연산자가 null이 될 수 있다고 말하지만 그 자체로는 실제로 어떤 일이 발생하는지 정의하지 않습니다.

둘째,의 의미를 변경하는 delete 0것은 주요 변경 사항이며 표준위원회가 이러한 특정 변경을 수행 할 가능성은 거의 없습니다. 또한 이것이 c++0x초안 의 호환성 부록 (부록 C)에 획기적인 변경이라는 언급이 없습니다 . 그러나 Annex C는 정보 섹션이므로 표준에 대한 해석이 없습니다.

반면에 null 포인터를 삭제해야 효과가 없다는 사실은 추가 런타임 검사를 의미합니다. 많은 코드에서 피연산자는 null이 될 수 없으므로이 런타임 검사는 제로 오버 헤드 원칙과 충돌합니다. 위원회는 언어의 명시된 디자인 목표에 맞게 표준 C ++를 더 많이 가져 오도록 동작을 변경하기로 결정했을 수도 있습니다.



답변

5.3.5 / 7 내용 :

delete-expression의 피연산자 값이 널 포인터 값이 아니면 delete-expression은 할당 해제 함수 (3.7.4.2)를 호출합니다. 그렇지 않으면 할당 해제 함수가 호출 될지 여부가 지정되지 않습니다.

그리고 3.7.4.2/3은 다음과 같이 말합니다.

할당 해제 함수에 제공된 첫 번째 인수의 값은 널 포인터 값일 수 있습니다. 그렇다면 할당 해제 함수가 표준 라이브러리에 제공된 함수이면 호출이 효과가 없습니다.

따라서 표준 할당 해제 함수를 사용하거나 사용자가 제공 한 할당 해제 함수가 널 포인터를 올바르게 처리하는 한 동작이 잘 정의되어 있습니다.


답변

반면에 null 포인터를 삭제해야 효과가 없다는 사실은 추가 런타임 검사를 의미합니다.

새로운 문구는 null 포인터에 대한 런타임 검사를 제거하지 않습니다. 다른 방법으로 표준 초안은 구현시 널 포인터 테스트를 준수 해야 한다고 말하는 것에 훨씬 더 가까워집니다 .

또한 주목할만한 점 : 이전 표준은 “삭제 피연산자의 값이 널 포인터이면 연산이 효과가 없다”고 (5.3.5 / 2)라고 말했지만 나중에 (5.3.5 / 7) “delete-expression은 할당 해제 함수를 호출합니다.” 함수 호출은 효과입니다. 호출 된 함수가 재정의 될 수 있기 때문에 특히 그렇습니다 operator delete.

새로운 문구는 그 모순을 제거하고 null 포인터를 삭제할 경우 할당 해제 함수가 호출되는지 여부를 구현에 명시 적으로 남겨 둡니다.


답변