programing

NULL 포인터가 C와 C++에서 다르게 정의되는 이유는 무엇입니까?

goodcopy 2022. 7. 23. 13:47
반응형

NULL 포인터가 C와 C++에서 다르게 정의되는 이유는 무엇입니까?

주식회사,NULL로 정의됩니다.(void *)0반면 C++에서는0.그것은 왜 그럴까?C에서 나는 이해할 수 있다.NULL에의 타입캐스트는 없습니다.(void *)컴파일러가 경고를 생성하거나 생성하지 않을 수 있습니다.이것 말고 다른 이유가 있나요?

C++03에서는 늘 포인터가 ISO 사양(§4.10/1)에 의해 다음과 같이 정의되었습니다.

Null 포인터 상수는 0으로 평가되는 정수 유형의 정수 상수 식(5.19) r 값입니다.

이것이 C++에서 쓸 수 있는 이유입니다.

int* ptr = 0;

C에서 이 규칙은 비슷하지만 조금 다릅니다(66.3.2.3/3).

값이 0인 정수 상수 표현식 또는 형식으로 캐스트된 표현식void *를 늘 포인터 상수라고 부릅니다.55) 늘 포인터 상수가 포인터 유형으로 변환되면 늘 포인터라고 불리는 결과 포인터는 오브젝트 또는 함수에 대한 포인터와 동등하지 않음을 보증합니다.

그 결과, 양쪽 모두

int* ptr = 0;

그리고.

int* ptr = (void *)0

합법입니다.하지만 제 추측으로는void*출연진들은 여기 있기 때문에

int x = NULL;

대부분의 시스템에서 컴파일러 경고를 생성합니다.C++ 에서는, 이것은 합법적이지 않습니다.이것은, 암묵적인 변환은 할 수 없기 때문입니다.void*캐스팅 없이 암시적으로 다른 포인터 유형으로 이동합니다.예를 들어, 이것은 불법입니다.

int* ptr = (void*)0; // Legal C, illegal C++

단, 코드 때문에 문제가 발생합니다.

int x = NULL;

정규 C++ 입니다.이것과 그 후의 혼란(나중에 나타내는 다른 케이스도 있습니다)에 의해, C++11 이후, 키워드가 있습니다.nullptrNull 포인터를 나타냅니다.

int* ptr = nullptr;

이것은 위의 문제는 없습니다.

또 다른 장점은nullptr0을 넘으면 C++ 타입의 시스템에서 더 잘 재생됩니다.예를 들어 다음과 같은 두 가지 기능이 있다고 가정합니다.

void DoSomething(int x);
void DoSomething(char* x);

내가 전화하면

DoSomething(NULL);

와 동등합니다.

DoSomething(0);

호출하는 것DoSomething(int)예상과는 달리DoSomething(char*)단,nullptr, 나는 쓸 수 있다.

DoSomething(nullptr);

그리고 그것은 그것을 호출할 것이다.DoSomething(char*)정상적으로 기능합니다.

마찬가지로, 예를 들면,vector<Object*>각 요소를 늘 포인터로 설정합니다.사용방법std::fill알고리즘, 내가 쓰려고 할 수도 있어.

std::fill(v.begin(), v.end(), NULL);

단, 템플릿시스템이 다음 처리를 하기 때문에 컴파일 되지 않습니다.NULL로서int포인터가 아니라이 문제를 해결하려면

std::fill(v.begin(), v.end(), (Object*)NULL);

이것은 보기 흉하고 템플릿시스템의 목적에 다소 어긋납니다.이 문제를 해결하려면nullptr:

std::fill(v.begin(), v.end(), nullptr);

그리고 그 이후로nullptr는 늘 포인터에 대응하는 타입(구체적으로는std::nullptr_t)이 올바르게 컴파일 됩니다.

이게 도움이 됐으면 좋겠네요!

주식회사,NULL는, 실장 정의의 「포인터 상수」로 전개됩니다.늘 포인터 상수는 값이 0인 정수 상수 표현식 또는 다음과 같은 표현식입니다.void*따라서 C의 실장에서는 다음과 같이 정의할 수 있습니다.NULL어느 쪽인가0또는 로서((void*)0).

C++에서는 늘 포인터 상수에 대한 규칙이 다릅니다.특히,((void*)0)C++ 늘 포인터 상수가 아니기 때문에 C++ 구현에서는 정의할 수 없습니다.NULL그와 같이.

C언어는 마이크로프로세서의 프로그래밍을 용이하게 하기 위해 만들어졌다.C 포인터는 데이터 주소를 메모리에 저장하기 위해 사용됩니다.포인터에 유효한 값이 없음을 나타내는 방법이 필요했습니다.주소 0은 모든 마이크로프로세서가 부팅을 위해 이 주소를 사용했기 때문에 선택되었습니다.다른 어떤 용도로도 사용할 수 없기 때문에 0은 유효한 값이 없는 포인터를 나타내는 좋은 선택입니다.C++는 C와의 하위 호환성이 있기 때문에 그 규칙을 계승합니다.

포인터로 사용할 때 0을 캐스팅해야 하는 것은 최근의 추가 사항일 뿐입니다.C의 후세대는 보다 엄밀하고(바람직히 에러가 적으면 좋겠다고 생각했기 때문에) 구문에 대해 보다 현학적인 태도를 보이기 시작했습니다.

언급URL : https://stackoverflow.com/questions/7016861/why-are-null-pointers-defined-differently-in-c-and-c

반응형