Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

Crate与源文件

Syntax
Crate
    InnerAttribute*
    Item*

注意

尽管Rust与其他任何语言一样,既可以由解释器实现,也可以由编译器实现,但目前唯一的实现是编译器,并且该语言始终被设计为可编译的。因此,本节假定存在一个编译器。

Rust的语义遵循编译期与运行期之间的 阶段区别1。具有 静态解释 的语义规则决定编译的成功或失败,而具有 动态解释 的语义规则决定程序在运行时的行为。

编译模型围绕称为 crate 的制品展开。每次编译都会处理一个源代码形式的单个crate,如果成功,则生成一个二进制形式的单个crate:一个可执行文件或某种库。2

一个 crate 是编译和链接的单元,也是版本控制、分发和运行时加载的单元。一个crate包含一个嵌套的模块作用域_树_。这棵树的顶层是一个匿名模块(从模块内部路径的角度来看),并且crate内的任何都有一个规范的模块路径,表示其在crate的模块树中的位置。

Rust编译器总是以单个源文件作为输入被调用,并总是生成单个输出crate。该源文件的处理可能会导致其他源文件作为模块被加载。源文件的扩展名为.rs

一个Rust源文件描述了一个模块,该模块的名称和位置——在当前crate的模块树中——是从源文件外部定义的:可以通过引用源文件中的显式Module项,或者通过crate本身的名称来定义。

每个源文件都是一个模块,但并非每个模块都需要自己的源文件:模块定义可以嵌套在一个文件中。

每个源文件包含零个或多个定义序列,并且可以选择以任意数量应用于包含模块的属性开头,其中大部分会影响编译器的行为。

匿名crate模块可以拥有适用于整个crate的额外属性。

注意

文件内容可以由shebang开头。

#![allow(unused)]
fn main() {
// 指定crate名称。
#![crate_name = "projx"]

// 指定输出制品类型。
#![crate_type = "lib"]

// 开启一个警告。
// 这可以在任何模块中完成,而不仅仅是匿名crate模块。
#![warn(non_camel_case_types)]
}

main函数

包含main函数的crate可以编译成可执行文件。

如果存在main函数,它必须不接受任何参数,不得声明任何特型或生命周期边界,不得有任何where子句,并且其返回类型必须实现Termination特型。

fn main() {}
fn main() -> ! {
    std::process::exit(0);
}
fn main() -> impl std::process::Termination {
    std::process::ExitCode::SUCCESS
}

main函数可以是一个导入,例如来自外部crate或当前crate。

#![allow(unused)]
fn main() {
mod foo {
    pub fn bar() {
        println!("Hello, world!");
    }
}
use foo::bar as main;
}

注意

标准库中实现了Termination的类型包括:

未捕获的外部unwinding

当“外部“unwind(例如从C++代码抛出的异常,或使用不同恐慌处理器的Rust代码中的panic!)传播超出main函数时,进程将安全终止。这可能以中止的形式发生,在这种情况下,不保证会执行任何Drop调用,并且错误输出可能不如运行时被“原生“Rust panic终止时那么详细。

欲了解更多信息,请参阅恐慌文档

no_main属性

no_main属性 可以应用于crate级别,以禁用为可执行二进制文件发出main符号。当链接到某个其他对象定义了main时,这会很有用。

crate_name属性

crate_name属性 可以应用于crate级别,使用MetaNameValueStr语法格式指定crate的名称。

#![allow(unused)]
#![crate_name = "mycrate"]
fn main() {
}

crate名称不能为空,并且只能包含Unicode字母数字字符或_(U+005F)字符。


  1. 这种区别也存在于解释器中。静态检查,如语法分析、类型检查和linting,无论程序何时执行,都应该在程序执行之前进行。

  2. 一个crate在某种程度上类似于ECMA-335 CLI模型中的assembly,SML/NJ Compilation Manager中的 库(library),Owens和Flatt模块系统中的 单元(unit),或Mesa中的 配置(configuration)