我们应该使用 Option 还是 ptr::null 来表示 Rust 中的空指针?

Posted

技术标签:

【中文标题】我们应该使用 Option 还是 ptr::null 来表示 Rust 中的空指针?【英文标题】:Should we use Option or ptr::null to represent a null pointer in Rust? 【发布时间】:2019-06-09 06:25:45 【问题描述】:

标准库的链表Nodeuses the Option type:

struct Node<T> 
    next: Option<NonNull<Node<T>>>,
    prev: Option<NonNull<Node<T>>>,
    element: T,

并使用以下代码创建一个节点:

Node 
    next: None,
    prev: None,
    element,

BTreeLeafNode的实现,标准库uses a raw pointer for the parent node:

struct LeafNode<K, V> 
    parent: *const InternalNode<K, V>,
    parent_idx: MaybeUninit<u16>,
    len: u16,
    keys: MaybeUninit<[K; CAPACITY]>,
    vals: MaybeUninit<[V; CAPACITY]>,

并创建新的叶节点by setting parent to ptr::null:

LeafNode 
    keys: MaybeUninit::uninitialized(),
    vals: MaybeUninit::uninitialized(),
    parent: ptr::null(),
    parent_idx: MaybeUninit::uninitialized(),
    len: 0

我们可以用nullptr在C++中实现上面的代码,那么Optionstd::ptr::null()代表空指针有什么区别呢?表示空指针的推荐方式是什么?

【问题讨论】:

你问的是Option&lt;NonNull&lt;T&gt;&gt;*mut T的区别吗? @E_net4wisheshappyholidays 我的意思是,Option和std::ptr::null()实现nullptr有什么区别,推荐哪种方式实现nullptr? 【参考方案1】:

一般来说,我建议使用NonNull&lt;T&gt; 而不是*const T*mut T,适当地使用Option 来识别指针何时可能为空。

原因有两个:

    在使用NonNull 时,null 是否为有效值已记录并强制*const T*mut T 本质上是可以互换的,并且确实可以相互转换,因此 constmut 可能会提供一种虚假的安全感。

BTree 的实现可能根本没有移植到 NonNull,这是相对较新的 - 它仅在 1.25 中稳定。

【讨论】:

NonNull 文档说:“如果您不确定是否应该使用 NonNull,请使用 *mut T!”

以上是关于我们应该使用 Option 还是 ptr::null 来表示 Rust 中的空指针?的主要内容,如果未能解决你的问题,请参考以下文章

为啥我们应该在颤振中使用选项?

有没有什么好的情况我们应该使用`unwrap`? [关闭]

让 select 的 option 标签支持事件监听(如复制操作)

Fiddler在fiddler option设置还是抓不了HTTPS包解决办法

关于期权池Option Pools与Vesting:码农创业防身必备法器

我应该如何使用&str,Option和String编组Rust函数并在C#中使用它?