08 June 2022

C++ 核心指南目录

F.23: Use a not_null<T> to indicate that “ null ” is not a valid value

理由

使得代码更清晰。函数的参数如果是not_null<T>的话,就要求调用函数的地方去确保,传入的参数不是空的。类似的,函数返回值是not_null<T>就是告诉函数的调用者,这个函数的返回值不会是空指针 nullptr ,就不需要进行额外检查。

例子

not_null<T*> 告诉使用者,指针取值的时候,不需要检测是否为空指针 nullptr 。另外,在调试的时候,owner<T*>not_null<T> 可以用来确保程序运行正确。

如下函数:

int length(Record* p);

当我调用length(p)的时候,我首先要检查 p 是否为空指针 nullptrlength() 的函数的实现是否需要检查 p 是否为空指针 nullptr 呢?

// 调用者确保 p != nullptr
int length(not_null<Record*> p);

// 函数实现者保证 p 可以是空指针
int length(Record* p);

注意

not_null<T*>强调这是个非空指针 nullptr ;而用T*则表示有可能是空指针。两者在内存中都以T*的形式表达。所以没什么额外运行时开销。

注意

not_null 不仅可用于指针,也能用于unique_ptrshared_ptr 以及其他指针类型。

强化

  • (简单)警告:函数中不进行非空判断,直接对原始指针取值的情况。建议把指针声明成 not_null
  • (简单)报错:原始指针有时候判断非空后取值,有时候直接取值。
  • (简单)警告:函数中对not_null指针进行非空测试。无此必要。