Learning Rust With Entirely Too Many Linked Lists篇文章中,作者提到:

但是,如果我们有一种特殊的枚举:

enum Foo {
    A,
    B(ContainsANonNullPtr),
}

空指针优化开始了,这是eliminates the space needed for the tag.如果变量为A,则整个枚举设置为所有0.否则,变量为B.这是因为B永远不可能都是0,因为它包含一个非零指针.

我猜作者是这么说的(假设A是4位,B是4位)

let test = Foo::A

内存布局是

0000 0000

但是

let test = Foo::B

内存布局是

some 8 bit non 0 value

这里到底优化了什么?这两种表示法不是都是8位吗?当作者声称

这意味着&&mutBoxRcArcVec和其他几种重要类型的 rust 迹在放入Option时没有开销

推荐答案

空指针优化基本上意味着,如果一个枚举有两个变量,其中一个变量没有关联数据,而另一个变量有关联数据,其中全零的位模式不是有效值,那么枚举本身将占用与关联值完全相同的空间量,使用全零位模式指示它是另一个变体.

换句话说,这意味着Option<&T>&T的大小完全相同,而不需要额外的单词.

Rust相关问答推荐

Rust,polars CSV:有没有一种方法可以从impll BufRead(或任何字节迭代器)中读取CSV?

Rust中的相互递归特性与默认实现

rust 蚀生命周期 行为

文档示例需要导入相关的 struct ,但仅在运行测试时.这是故意的行为吗?

在自身功能上实现类似移动的行为,以允许通过大小的所有者进行呼叫(&;mut;self)?

如果成员都实现特征,是否在多态集合上实现部分重叠的特征?

将数组转换为HashMap的更简单方法

为什么`AlternateScreen`在读取输入键时需要按Enter键?

为什么BufReader实际上没有缓冲短寻道?

提取指向特征函数的原始指针

详尽的匹配模式绑定

Rust 中指向自身的引用如何工作?

如何获取模块树?

bcrypt 有长度限制吗?

使用 traits 时,borrow 的值不会存在足够长的时间

为什么传递 option.as_ref 的行为不同于使用匹配块并将内部映射到 ref 自己?

如何创建递归borrow 其父/创建者的 struct ?

我如何将 google_gmail1::Gmail> 传递给线程生成?

如何在 Rust 的内置函数上实现特征?

为什么 `ref` 会导致此示例*取消引用*一个字段?