mirror of
https://github.com/changkun/modern-cpp-tutorial.git
synced 2025-12-16 20:27:08 +03:00
book: fix imprecise description of NULL in C++ (#279)
This commit is contained in:
@@ -18,20 +18,21 @@ which refers to the language behavior that occurred before the runtime.
|
||||
|
||||
### nullptr
|
||||
|
||||
The purpose of `nullptr` appears to replace `NULL`. In a sense,
|
||||
traditional C++ treats `NULL` and `0` as the same thing,
|
||||
depending on how the compiler defines NULL,
|
||||
and some compilers define NULL as `((void*)0)` Some will define it directly as `0`.
|
||||
The purpose of `nullptr` appears to replace `NULL`. There are **null pointer constants** in the C and C++ languages,
|
||||
which can be implicitly converted to null pointer value of any pointer type,
|
||||
or null member pointer value of any pointer-to-member type in C++.
|
||||
`NULL` is provided by the standard library implementation and defined as an implementation-defined null pointer constant.
|
||||
In C, some standard libraries defines `NULL` as `((void*)0)` and some define it as `0`.
|
||||
|
||||
C++ **does not allow** to implicitly convert `void *` to other types.
|
||||
But if the compiler tries to define `NULL` as `((void*)0)`, then in the following code:
|
||||
C++ **does not allow** to implicitly convert `void *` to other types, and thus `((void*)0)` is not a valid implementation
|
||||
of `NULL`. If the standard library tries to define `NULL` as `((void*)0)`, then compilation error would occur in the following code:
|
||||
|
||||
```cpp
|
||||
char *ch = NULL;
|
||||
```
|
||||
|
||||
C++ without the `void *` implicit conversion has to define `NULL` as `0`.
|
||||
This still creates a new problem. Defining `NULL` to 0 will cause the overloading feature in `C++` to be confusing.
|
||||
This still creates a new problem. Defining `NULL` to `0` will cause the overloading feature in `C++` to be confusing.
|
||||
Consider the following two `foo` functions:
|
||||
|
||||
```cpp
|
||||
@@ -41,7 +42,7 @@ void foo(int);
|
||||
|
||||
Then the `foo(NULL);` statement will call `foo(int)`, which will cause the code to be counterintuitive.
|
||||
|
||||
To solve this problem, C++11 introduced the `nullptr` keyword, which is specifically used to distinguish null pointers, 0. The type of `nullptr` is `nullptr_t`, which can be implicitly converted to any pointer or member pointer type, and can be compared equally or unequally with them.
|
||||
To solve this problem, C++11 introduced the `nullptr` keyword, which is specifically used to distinguish null pointers, `0`. The type of `nullptr` is `nullptr_t`, which can be implicitly converted to any pointer or member pointer type, and can be compared equally or unequally with them.
|
||||
|
||||
You can try to compile the following code using clang++:
|
||||
|
||||
|
||||
@@ -14,9 +14,9 @@ order: 2
|
||||
|
||||
### nullptr
|
||||
|
||||
`nullptr` 出现的目的是为了替代 `NULL`。在某种意义上来说,传统 C++ 会把 `NULL`、`0` 视为同一种东西,这取决于编译器如何定义 `NULL`,有些编译器会将 `NULL` 定义为 `((void*)0)`,有些则会直接将其定义为 `0`。
|
||||
`nullptr` 出现的目的是为了替代 `NULL`。 C 与 C++ 语言中有**空指针常量**,它们能被隐式转换成任何指针类型的空指针值,或 C++ 中的任何成员指针类型的空成员指针值。 `NULL` 由标准库实现提供,并被定义为实现定义的空指针常量。在 C 中,有些标准库会把 `NULL` 定义为 `((void*)0)` 而有些将它定义为 `0`。
|
||||
|
||||
C++ **不允许**直接将 `void *` 隐式转换到其他类型。但如果编译器尝试把 `NULL` 定义为 `((void*)0)`,那么在下面这句代码中:
|
||||
C++ **不允许**直接将 `void *` 隐式转换到其他类型,从而 `((void*)0)` 不是 `NULL` 的合法实现。如果标准库尝试把 `NULL` 定义为 `((void*)0)`,那么下面这句代码中会出现编译错误:
|
||||
|
||||
```cpp
|
||||
char *ch = NULL;
|
||||
|
||||
Reference in New Issue
Block a user