我正在编写一个带有单元测试的 Rust 库(从货物生成)。
我想在我的单元测试中使用 extern crate maplit以便能够使用类似 JavaScript 的 hashmap 文字。我不想在我的库代码中使用 maplit。
maplit 提供了一个显然必须使用#[macro_use] 激活的宏。我能够让这一切正常工作的唯一方法是将它放在顶部lib.rs:
#[cfg(test)] #[macro_use] extern crate maplit;
// my crate-specific stuff
Run Code Online (Sandbox Code Playgroud)
在这一点上,我意识到我不知道 #[cfg(test)] 到底是做什么的。我在我的测试中使用它。根据约定,这些包含在库代码中,如下所示:
// some library code
#[cfg(test)]
mod test {
use super::*;
// tests here
}
Run Code Online (Sandbox Code Playgroud)
我原以为#[cfg(test)] 行将文件(或块?)结束之前的内容标记为仅适用于测试配置。
如果是这样,那么将此指令放在顶部lib.rs似乎是一个问题。当我编译一个发行版时,我的整个库不会被删除吗?
我试图找到有关 #[cfg(test)] 究竟做了什么的文档,但无济于事。
Rea*_*lar 15
#[....]
Run Code Online (Sandbox Code Playgroud)
上面是一个Rust 属性,它就像其他语言中的注释。例如; 在 Java 中,我们有@Annotation(....)方法和类。与注解不同,rust 属性可以是遵循属性语法的表达式。
#[....]
Run Code Online (Sandbox Code Playgroud)
#[cfg(....)]
Run Code Online (Sandbox Code Playgroud)
上面告诉 Rust 编译器,下面的代码应该只在test配置处于活动状态时编译。您可以拥有其他配置属性,例如debug,windows或 features。
#[cfg(test)]
Run Code Online (Sandbox Code Playgroud)
是相同的
#[cfg(test)] #[macro_use] extern crate maplit;
Run Code Online (Sandbox Code Playgroud)
这告诉 Rust 编译器仅在test配置处于活动状态时编译下一行,而下一行告诉 Rust 仅使用来自以下 crate 的宏。
如果是这样,那么将此指令放在 lib.rs 的顶部似乎是一个问题。当我编译一个发行版时,我的整个库不会被删除吗?
该#[cfg(...)]属性仅将编译器条件应用于它所附加的事物。
当您将属性放在文件顶部时,后跟一个空格。该属性附加到当前模块或板条箱。
如文档示例中所示,crate_type应用于整个文件:
#[cfg(test)]
#[macro_use]
extern crate maplit;
Run Code Online (Sandbox Code Playgroud)