Rust 1.38.0 发布公告

2019 年 9 月 26 日 · Rust 发布团队

Rust 团队很高兴地宣布 Rust 的新版本 1.38.0。Rust 是一种编程语言,旨在赋能所有人构建可靠且高效的软件。

如果您之前通过 rustup 安装了 Rust,那么获取 Rust 1.38.0 非常简单,只需执行:

$ rustup update stable

如果您尚未安装,可以从我们网站上的相应页面获取 rustup

1.38.0 稳定版的新特性

此版本的亮点是流水线编译。

流水线编译

要编译一个 crate,编译器不需要依赖项被完全构建。相反,它只需要它们的“元数据”(即类型、依赖项、导出列表...)。此元数据在编译过程的早期生成。从 Rust 1.38.0 开始,Cargo 将利用这一点,在元数据准备就绪后立即自动开始构建依赖的 crate。

虽然此更改对单个 crate 的构建没有任何影响,但在测试期间,我们收到了报告,表明对于某些 crate 图的优化、干净构建,编译速度提高了 10-20%。其他一些 crate 图的改进不大,速度提升取决于运行构建的硬件,因此您的结果可能会有所不同。无需任何代码更改即可从中受益。

mem::{uninitialized, zeroed} 的一些不正确用法进行 lint

正如之前宣布的std::mem::uninitialized 本质上不可能安全使用。相反,应该使用 MaybeUninit<T>

我们尚未弃用 mem::uninitialized;这将在未来的版本中完成。但是,从 1.38.0 开始,rustc 将为使用 mem::uninitializedmem::zeroed 的一小类不正确的初始化提供 lint。

对于某些类型(例如 &TBox<T>),永远包含全 0 位模式是未定义行为,因为它们表示不能为 null 的类指针对象。因此,使用 mem::uninitializedmem::zeroed 初始化这些类型之一是错误的,因此新的 lint 将尝试在任何时候警告使用这些函数之一来初始化其中一种类型,无论是直接初始化还是作为较大 struct 的成员进行初始化。检查是递归的,因此以下代码将发出警告

struct Wrap<T>(T);
struct Outer(Wrap<Wrap<Wrap<Box<i32>>>>);
struct CannotBeZero {
    outer: Outer,
    foo: i32,
    bar: f32
}

...

let bad_value: CannotBeZero = unsafe { std::mem::uninitialized() };

精明的读者可能会注意到,Rust 还有更多类型不能为零,特别是 NonNull<T>NonZero<T>。目前,使用 mem::uninitializedmem::zeroed 初始化这些结构体不会被 lint。

这些检查并未涵盖 mem::uninitializedmem::zeroed 的所有不安全使用情况,它们仅有助于识别肯定是错误的代码。所有代码仍应迁移到使用 MaybeUninit

#[deprecated]

#[deprecated] 属性最早在 Rust 1.9.0 中引入,允许 crate 作者通知其用户,他们 crate 的某个项已被弃用,并将在未来的版本中删除。Rust 1.38.0 扩展了此属性,允许将其应用于宏。

std::any::type_name

为了进行调试,有时需要获取类型的名称。例如,在泛型代码中,您可能想在运行时查看函数的类型参数被实例化为哪些具体类型。现在可以使用 std::any::type_name 来完成此操作

fn gen_value<T: Default>() -> T {
    println!("Initializing an instance of {}", std::any::type_name::<T>());
    Default::default()
}

fn main() {
    let _: i32 = gen_value();
    let _: String = gen_value();
}

这将打印

Initializing an instance of i32
Initializing an instance of alloc::string::String

与所有仅用于调试的标准库函数一样,字符串的确切内容和格式没有保证。返回的值仅是对类型的尽力描述;多种类型可能共享相同的 type_name 值,并且该值可能会在未来的编译器版本中更改。

库变更

此外,以下函数已稳定化

其他变更

Rust 1.38 版本中还有其他更改:请查看 RustCargoClippy 中的更改。

更正

此帖子的先前版本错误地将以下函数标记为稳定版。它们尚未稳定。Duration::div_duration_f32Duration::div_duration_f64

1.38.0 版本贡献者

许多人齐心协力创建了 Rust 1.38.0。没有大家,我们不可能做到。感谢!