Maximally minimal view types

作者: Nikomatsakis (Rust核心团队) | 日期: 2026-03-21 | ⭐⭐⭐⭐ 4星

摘要

Rust语言View Types提案,解决借用检查器痛点。当前Rust在drain循环中调用self方法会报错,因为借用检查器不知道方法只访问某些字段。View Types允许显式声明方法将访问哪些字段。

核心亮点

1. 当前问题

假设有一个MessageProcessor结构体,包含消息和统计信息:

pub struct MessageProcessor {
    messages: Vec<String>,
    statistics: Statistics,
}

fn process_pushed_messages(&mut self) {
    for message in self.messages.drain(..) {
        self.process_message(message); // <-- ERROR: `self` is borrowed
    }
}

fn process_message(&mut self, message: String) {
    self.statistics.message_count += 1;
    self.statistics.total_bytes += message.len();
}

问题在于:self.messages.drain(..)借用self.messages。当调用self.process_message时,编译器假设你可能修改任何字段,包括self.messages,因此报错。

2. View Types解决方案

View Types允许你声明方法只访问特定字段:

fn process_message(&mut self {statistics}, message: String) {
    //                ----------------
    //                简写: `self: &mut MessageProcessor {statistics}`
    self.statistics.message_count += 1;
    self.statistics.total_bytes += message.len();
}

3. 语法扩展

View Types扩展了结构体类型的语法,可选择包含可访问字段列表:

RustType := StructName<...>
         |  StructName<...> { .. }         // 所有字段可访问
         |  StructName<...> { (fields),* } // 指定字段可访问

4. 借用检查器如何工作

集成Views到借用检查器非常简单。借用检查器在看到借用表达式时,会记录"贷款",跟踪被借用的位置、借用的方式(mut/shared)和生命周期。

对于View Types,我们记录多个贷款而不是单个贷款。例如:

  • &mut self → 记录一个mut贷款
  • &mut self {field1, field2} → 记录两个mut贷款:self.field1self.field2

5. 运行时无开销

View Types是纯静态构造,不改变编译方式。process_message方法仍然只接受一个指向self的指针。

6. 实现难度

"坦率说,不难。如果我们找到一个想要承担的贡献者,我认为今年就可以发货。"

核心洞察

"借用的核心问题是:借用检查器不知道process_message方法将访问statistics字段。"

相关链接


原文链接